Fix most of the polling issues relating to disabled targets: - Disable polling while running TAP event handlers ... the handlers rely on state machine transitions which polling will break.
- Don't background-poll disabled TAPs ... this was just a bug waiting to happen. (And then it happened!) - Don't fail command line polls of disabled taps; that's not any kind of error, it's just that you can't do much. - Spell "continuous" correctly in the variable name. ;) I say "most" issues since (a) there's no interlock between a polling context and anything else, which may eventually trigger SMP issues; and (b) this is one of several areas where the jtag and target layers could stand to interact more cleanly. --- src/jtag/tcl.c | 12 ++++++++++++ src/target/target.c | 34 +++++++++++++++++++++------------- src/target/target.h | 2 ++ 3 files changed, 35 insertions(+), 13 deletions(-)
Fix most of the polling issues relating to disabled targets: - Disable polling while running TAP event handlers ... the handlers rely on state machine transitions which polling will break. - Don't background-poll disabled TAPs ... this was just a bug waiting to happen. (And then it happened!) - Don't fail command line polls of disabled taps; that's not any kind of error, it's just that you can't do much. - Spell "continuous" correctly in the variable name. ;) I say "most" issues since (a) there's no interlock between a polling context and anything else, which may eventually trigger SMP issues; and (b) this is one of several areas where the jtag and target layers could stand to interact more cleanly. --- src/jtag/tcl.c | 12 ++++++++++++ src/target/target.c | 34 +++++++++++++++++++++------------- src/target/target.h | 2 ++ 3 files changed, 35 insertions(+), 13 deletions(-) --- a/src/jtag/tcl.c +++ b/src/jtag/tcl.c @@ -35,6 +35,8 @@ #include "minidriver.h" #include "interface.h" +#include "target.h" + #ifdef HAVE_STRINGS_H #include <strings.h> #endif @@ -465,9 +467,18 @@ static int jim_newtap_cmd( Jim_GetOptInf static void jtag_tap_handle_event( jtag_tap_t * tap, enum jtag_tap_event e) { + int saved_pollval = target_continuous_poll; jtag_tap_event_action_t * jteap; int done; + /* Don't let background polling interfere with TAP enable/disable + * logic, which depend on nuances of the JTAG state machine. + * + * NOTE: we not only want it not to start ... we want any poll + * that was currently active to have finished. + */ + target_continuous_poll = 0; + jteap = tap->event_action; done = 0; @@ -492,6 +503,7 @@ static void jtag_tap_handle_event( jtag_ e, Jim_Nvp_value2name_simple( nvp_jtag_tap_event, e)->name); } + target_continuous_poll = saved_pollval; } --- a/src/target/target.c +++ b/src/target/target.c @@ -269,7 +269,7 @@ static int new_target_number(void) return x+1; } -static int target_continous_poll = 1; +int target_continuous_poll = 1; /* read a u32 from a buffer in target memory endianness */ u32 target_buffer_get_u32(target_t *target, const u8 *buffer) @@ -436,13 +436,13 @@ int target_process_reset(struct command_ * more predictable, i.e. dr/irscan & pathmove in events will * not have JTAG operations injected into the middle of a sequence. */ - int save_poll = target_continous_poll; - target_continous_poll = 0; + int save_poll = target_continuous_poll; + target_continuous_poll = 0; sprintf( buf, "ocd_process_reset %s", n->name ); retval = Jim_Eval( interp, buf ); - target_continous_poll = save_poll; + target_continuous_poll = save_poll; if(retval != JIM_OK) { Jim_PrintErrorMessage(interp); @@ -1650,20 +1650,23 @@ int handle_target(void *priv) recursive = 0; } - target_t *target = all_targets; - - while (target) + /* Poll targets for state changes unless that's globally disabled. + * Skip targets that are currently disabled. + */ + for (target_t *target = all_targets; + target_continuous_poll && target; + target = target->next) { + if (!target->tap->enabled) + continue; /* only poll target if we've got power and srst isn't asserted */ - if (target_continous_poll&&!powerDropout&&!srstAsserted) + if (!powerDropout && !srstAsserted) { /* polling may fail silently until the target has been examined */ if((retval = target_poll(target)) != ERROR_OK) return retval; } - - target = target->next; } return retval; @@ -1791,7 +1794,12 @@ static int handle_poll_command(struct co if (argc == 0) { command_print(cmd_ctx, "background polling: %s", - target_continous_poll ? "on" : "off"); + target_continuous_poll ? "on" : "off"); + command_print(cmd_ctx, "TAP: %s (%s)", + target->tap->dotted_name, + target->tap->enabled ? "enabled" : "disabled"); + if (!target->tap->enabled) + return ERROR_OK; if ((retval = target_poll(target)) != ERROR_OK) return retval; if ((retval = target_arch_state(target)) != ERROR_OK) @@ -1802,11 +1810,11 @@ static int handle_poll_command(struct co { if (strcmp(args[0], "on") == 0) { - target_continous_poll = 1; + target_continuous_poll = 1; } else if (strcmp(args[0], "off") == 0) { - target_continous_poll = 0; + target_continuous_poll = 0; } else { --- a/src/target/target.h +++ b/src/target/target.h @@ -244,6 +244,8 @@ extern int target_call_timer_callbacks(v */ extern int target_call_timer_callbacks_now(void); +extern int target_continuous_poll; + extern target_t* get_current_target(struct command_context_s *cmd_ctx); extern int get_num_by_target(target_t *query_target); extern target_t *get_target(const char *id);
_______________________________________________ Openocd-development mailing list Openocd-development@lists.berlios.de https://lists.berlios.de/mailman/listinfo/openocd-development