]> www.infradead.org Git - users/borneoa/openocd-next.git/commitdiff
jtag/vdebug: implement a polling mechanism
authorJacek Wuwer <jacekmw8@gmail.com>
Wed, 24 Apr 2024 08:15:38 +0000 (10:15 +0200)
committerAntonio Borneo <borneo.antonio@gmail.com>
Sat, 7 Jun 2025 10:05:05 +0000 (10:05 +0000)
This change adds a polling mechanism to the driver. When not busy
the driver issues a wait, allowing the target to advance time.
The wait period gets adjusted to match the polling setting.

Change-Id: I67f481d05d7c5ce5352b5cb97de78dbaa97d82ae
Signed-off-by: Jacek Wuwer <jacekmw8@gmail.com>
Reviewed-on: https://review.openocd.org/c/openocd/+/8221
Reviewed-by: Antonio Borneo <borneo.antonio@gmail.com>
Tested-by: jenkins
src/jtag/drivers/vdebug.c
tcl/board/vd_a75x4_jtag.cfg
tcl/board/vd_pulpissimo_jtag.cfg
tcl/interface/vdebug.cfg
tcl/target/vd_riscv.cfg

index 38685950a880daa3debfaea9099a713fb2ce9441..29bfa8360dde0bf0f2e185423e04032627202067 100644 (file)
 #include "jtag/interface.h"
 #include "jtag/commands.h"
 #include "transport/transport.h"
+#include "target/target.h"
 #include "target/arm_adi_v5.h"
 #include "helper/time_support.h"
 #include "helper/replacements.h"
 #include "helper/log.h"
 #include "helper/list.h"
 
-#define VD_VERSION 48
+#define VD_VERSION 50
 #define VD_BUFFER_LEN 4024
 #define VD_CHEADER_LEN 24
 #define VD_SHEADER_LEN 16
 
 #define VD_MAX_MEMORIES 20
-#define VD_POLL_INTERVAL 500
+#define VD_POLL_INTERVAL 1000
 #define VD_SCALE_PSTOMS 1000000000
 
 /**
@@ -205,6 +206,7 @@ struct vd_client {
        uint32_t poll_max;
        uint32_t targ_time;
        int hsocket;
+       int64_t poll_ts;
        char server_name[32];
        char bfm_path[128];
        char mem_path[VD_MAX_MEMORIES][128];
@@ -839,6 +841,35 @@ static void vdebug_mem_close(int hsock, struct vd_shm *pm, uint8_t ndx)
 }
 
 
+/* function gets invoked through a callback every VD_POLL_INTERVAL ms
+ * if the idle time, measured by VD_POLL_INTERVAL - targ_time is more than poll_min
+ * the wait function is called and its time measured and wait cycles adjusted.
+ * The wait allows hardware to advance, when no data activity from the vdebug occurs
+ */
+static int vdebug_poll(void *priv)
+{
+       int64_t ts, te;
+
+       ts = timeval_ms();
+       if (ts - vdc.poll_ts - vdc.targ_time >= vdc.poll_min) {
+               vdebug_wait(vdc.hsocket, pbuf, vdc.poll_cycles);
+               te = timeval_ms();
+               LOG_DEBUG("poll after %" PRId64 "ms, busy %" PRIu32 "ms; wait %" PRIu32 " %" PRId64 "ms",
+                       ts - vdc.poll_ts, vdc.targ_time, vdc.poll_cycles, te - ts);
+
+               if (te - ts + vdc.targ_time < vdc.poll_max / 2)
+                       vdc.poll_cycles *= 2;
+               else if (te - ts + vdc.targ_time > vdc.poll_max)
+                       vdc.poll_cycles /= 2;
+       } else {
+               LOG_DEBUG("poll after %" PRId64 "ms, busy %" PRIu32 "ms", ts - vdc.poll_ts, vdc.targ_time);
+       }
+       vdc.poll_ts = ts;
+       vdc.targ_time = 0;                 /* reset target time counter */
+
+       return ERROR_OK;
+}
+
 static int vdebug_init(void)
 {
        vdc.hsocket = vdebug_socket_open(vdc.server_name, vdc.server_port);
@@ -858,6 +889,7 @@ static int vdebug_init(void)
        }
        vdc.trans_first = 1;
        vdc.poll_cycles = vdc.poll_max;
+       vdc.poll_ts = timeval_ms();
        uint32_t sig_mask = VD_SIG_RESET;
        if (transport_is_jtag())
                sig_mask |= VD_SIG_TRST | VD_SIG_TCKDIV;
@@ -876,6 +908,8 @@ static int vdebug_init(void)
                                LOG_ERROR("0x%x cannot connect to %s", rc, vdc.mem_path[i]);
                }
 
+               target_register_timer_callback(vdebug_poll, VD_POLL_INTERVAL,
+                                                                          TARGET_TIMER_TYPE_PERIODIC, &vdc);
                LOG_INFO("vdebug %d connected to %s through %s:%" PRIu16,
                                 VD_VERSION, vdc.bfm_path, vdc.server_name, vdc.server_port);
        }
@@ -885,6 +919,8 @@ static int vdebug_init(void)
 
 static int vdebug_quit(void)
 {
+       target_unregister_timer_callback(vdebug_poll, &vdc);
+
        for (uint8_t i = 0; i < vdc.mem_ndx; i++)
                if (vdc.mem_width[i])
                        vdebug_mem_close(vdc.hsocket, pbuf, i);
@@ -1299,16 +1335,16 @@ static const struct command_registration vdebug_command_handlers[] = {
        {
                .name = "batching",
                .handler = &vdebug_set_batching,
-               .mode = COMMAND_CONFIG,
+               .mode = COMMAND_ANY,
                .help = "set the transaction batching no|wr|rd [0|1|2]",
                .usage = "<level>",
        },
        {
                .name = "polling",
                .handler = &vdebug_set_polling,
-               .mode = COMMAND_CONFIG,
-               .help = "set the polling pause, executing hardware cycles between min and max",
-               .usage = "<min cycles> <max cycles>",
+               .mode = COMMAND_ANY,
+               .help = "set the min idle time and max wait time in ms",
+               .usage = "<min_idle> <max_wait>",
        },
        COMMAND_REGISTRATION_DONE
 };
index c94a71972dcebd6e603b37833c7ab66552bed78e..a91f8b8cfc41dd3d00324efd4bab0806a1a8fbeb 100644 (file)
@@ -17,7 +17,7 @@ set CPUTAPID 0x4ba06477
 transport select jtag
 
 # JTAG reset config, frequency and reset delay
-reset_config trst_and_srst
+reset_config trst_only
 adapter speed 1500000
 adapter srst delay 5
 
index a3f5a848865f84248254617571f6a37555532ca8..5a6725fd62a84b49a81d5f133f1d643622afb07c 100644 (file)
@@ -4,9 +4,9 @@
 
 source [find interface/vdebug.cfg]
 
-set _CHIPNAME ibex
-set _HARTID 0x20
-set _CPUTAPID 0x249511c3
+set CHIPNAME ibex
+set HARTID 0x20
+set CPUTAPID 0x249511c3
 
 # vdebug select transport
 transport select jtag
@@ -25,7 +25,7 @@ vdebug mem_path tbench.soc_domain_i.pulp_soc_i.gen_mem_l2_pri\[1\].sram_i.mem_ar
 vdebug mem_path tbench.soc_domain_i.pulp_soc_i.gen_mem_l2\[0\].sram_i.mem_array 0x1c010000 0x80000
 
 # need to explicitly define riscv tap, autoprobing does not work for icapture != 0x01
-jtag newtap $_CHIPNAME cpu -irlen 5 -ircapture 0x05 -irmask 0x1f -expected-id $_CPUTAPID
+jtag newtap $CHIPNAME cpu -irlen 5 -ircapture 0x05 -irmask 0x1f -expected-id $CPUTAPID
 
 jtag arp_init-reset
 
index 63a595506797b44f8f6adb3489538d412a699ed9..27a8aafd7bf39e9069b172028e54e358f035777c 100644 (file)
@@ -30,4 +30,4 @@ tcl port disabled
 vdebug batching 1
 
 # Polling values
-vdebug polling 100 1000
+vdebug polling 100 500
index f08cb1ac8be0148b171ff2065cc58a1c391ca88b..44a80524a6b51877b44291770420ab41ff357a53 100644 (file)
@@ -2,15 +2,15 @@
 # Cadence virtual debug interface
 # RISCV core
 
-if {![info exists _HARTID]} {
-       set _HARTID 0x00
+if {![info exists HARTID]} {
+       set HARTID 0x00
 }
-if {![info exists _CHIPNAME]} {
-       set _CHIPNAME riscv
+if {![info exists CHIPNAME]} {
+       set CHIPNAME riscv
 }
-set _TARGETNAME $_CHIPNAME.cpu
+set _TARGETNAME $CHIPNAME.cpu
 
-target create $_TARGETNAME riscv -chain-position $_TARGETNAME -coreid $_HARTID
+target create $_TARGETNAME riscv -chain-position $_TARGETNAME -coreid $HARTID
 
 riscv set_reset_timeout_sec 120
 riscv set_command_timeout_sec 120