#endif
-int jtag_flush_queue_count; /* count # of flushes for profiling / debugging purposes */
+/// The number of JTAG queue flushes (for profiling and debugging purposes).
+static int jtag_flush_queue_count;
static void jtag_add_scan_check(void (*jtag_add_scan)(int in_num_fields, const scan_field_t *in_fields, tap_state_t state),
int in_num_fields, scan_field_t *in_fields, tap_state_t state);
int jtag_trst = 0;
int jtag_srst = 0;
-static jtag_tap_t *jtag_all_taps = NULL;
+/**
+ * List all TAPs that have been created.
+ */
+static jtag_tap_t *__jtag_all_taps = NULL;
+/**
+ * The number of TAPs in the __jtag_all_taps list, used to track the
+ * assigned chain position to new TAPs
+ */
+static int jtag_num_taps = 0;
enum reset_types jtag_reset_config = RESET_NONE;
tap_state_t cmd_queue_end_state = TAP_RESET;
/* speed in kHz*/
static int speed_khz = 0;
/* flag if the kHz speed was defined */
-static int hasKHz = 0;
+static bool hasKHz = false;
/* jtag interfaces (parport, FTDI-USB, TI-USB, ...)
*/
static int handle_verify_jtag_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
static int handle_tms_sequence_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
-jtag_tap_t *jtag_AllTaps(void)
+jtag_tap_t *jtag_all_taps(void)
{
- return jtag_all_taps;
+ return __jtag_all_taps;
};
-int jtag_NumTotalTaps(void)
+int jtag_tap_count(void)
{
- jtag_tap_t *t;
- int n;
-
- n = 0;
- t = jtag_AllTaps();
- while(t){
- n++;
- t = t->next_tap;
- }
- return n;
+ return jtag_num_taps;
}
int jtag_NumEnabledTaps(void)
int n;
n = 0;
- t = jtag_AllTaps();
+ t = jtag_all_taps();
while(t){
if( t->enabled ){
n++;
return n;
}
-jtag_tap_t *jtag_TapByString( const char *s )
+/// Append a new TAP to the chain of all taps.
+static void jtag_tap_add(struct jtag_tap_s *t)
+{
+ t->abs_chain_position = jtag_num_taps++;
+
+ jtag_tap_t **tap = &__jtag_all_taps;
+ while(*tap != NULL)
+ tap = &(*tap)->next_tap;
+ *tap = t;
+}
+
+jtag_tap_t *jtag_tap_by_string( const char *s )
{
jtag_tap_t *t;
char *cp;
- t = jtag_AllTaps();
+ t = jtag_all_taps();
/* try name first */
while(t){
if( 0 == strcmp( t->dotted_name, s ) ){
n = strtol( s, &cp, 0 );
if( (s != cp) && (*cp == 0) ){
/* Then it is... */
- t = jtag_TapByAbsPosition(n);
+ t = jtag_tap_by_abs_position(n);
}
}
return t;
}
-jtag_tap_t * jtag_TapByJimObj( Jim_Interp *interp, Jim_Obj *o )
+jtag_tap_t * jtag_tap_by_jim_obj( Jim_Interp *interp, Jim_Obj *o )
{
jtag_tap_t *t;
const char *cp;
cp = "(unknown)";
t = NULL;
} else {
- t = jtag_TapByString( cp );
+ t = jtag_tap_by_string( cp );
}
if( t == NULL ){
Jim_SetResult_sprintf(interp,"Tap: %s is unknown", cp );
}
/* returns a pointer to the n-th device in the scan chain */
-jtag_tap_t * jtag_TapByAbsPosition( int n )
+jtag_tap_t * jtag_tap_by_abs_position( int n )
{
int orig_n;
jtag_tap_t *t;
orig_n = n;
- t = jtag_AllTaps();
+ t = jtag_all_taps();
while( t && (n > 0)) {
n--;
return t;
}
+const char *jtag_tap_name(const jtag_tap_t *tap)
+{
+ return (tap == NULL) ? "(unknown)" : tap->dotted_name;
+}
+
+
int jtag_register_event_callback(int (*callback)(enum jtag_event event, void *priv), void *priv)
{
jtag_event_callback_t **callbacks_p = &jtag_event_callbacks;
if (trst_with_tlr)
{
LOG_DEBUG("JTAG reset with RESET instead of TRST");
- jtag_add_end_state(TAP_RESET);
+ jtag_set_end_state(TAP_RESET);
jtag_add_tlr();
return;
}
}
}
-tap_state_t jtag_add_end_state(tap_state_t state)
+tap_state_t jtag_set_end_state(tap_state_t state)
{
if ((state == TAP_DRSHIFT)||(state == TAP_IRSHIFT))
{
return;
}
-static const char *jtag_tap_name(const jtag_tap_t *tap)
-{
- return (tap == NULL) ? "(unknown)" : tap->dotted_name;
-}
-
int jtag_check_value_inner(u8 *captured, u8 *in_check_value, u8 *in_check_mask, int num_bits)
{
int retval = ERROR_OK;
}
}
+int jtag_get_flush_queue_count(void)
+{
+ return jtag_flush_queue_count;
+}
+
int jtag_execute_queue(void)
{
int retval;
return retval;
}
-int jtag_reset_callback(enum jtag_event event, void *priv)
+static int jtag_reset_callback(enum jtag_event event, void *priv)
{
jtag_tap_t *tap = priv;
/* Try to examine chain layout according to IEEE 1149.1 ยง12
*/
-int jtag_examine_chain(void)
+static int jtag_examine_chain(void)
{
jtag_tap_t *tap;
scan_field_t field;
if (device_count != jtag_NumEnabledTaps())
{
LOG_ERROR("number of discovered devices in JTAG chain (%i) doesn't match (enabled) configuration (%i), total taps: %d",
- device_count, jtag_NumEnabledTaps(), jtag_NumTotalTaps());
+ device_count, jtag_NumEnabledTaps(), jtag_tap_count());
LOG_ERROR("check the config file and ensure proper JTAG communication (connections, speed, ...)");
return ERROR_JTAG_INIT_FAILED;
}
return ERROR_OK;
}
-int jtag_validate_chain(void)
+static int jtag_validate_chain(void)
{
jtag_tap_t *tap;
int total_ir_length = 0;
return JIM_OK;
}
+
+static void jtag_tap_init(jtag_tap_t *tap)
+{
+ assert(0 != tap->ir_length);
+
+ tap->expected = malloc(tap->ir_length);
+ tap->expected_mask = malloc(tap->ir_length);
+ tap->cur_instr = malloc(tap->ir_length);
+
+ buf_set_u32(tap->expected, 0, tap->ir_length, tap->ir_capture_value);
+ buf_set_u32(tap->expected_mask, 0, tap->ir_length, tap->ir_capture_mask);
+ buf_set_ones(tap->cur_instr, tap->ir_length);
+
+ // place TAP in bypass mode
+ tap->bypass = 1;
+ // register the reset callback for the TAP
+ jtag_register_event_callback(&jtag_reset_callback, tap);
+
+ LOG_DEBUG("Created Tap: %s @ abs position %d, "
+ "irlen %d, capture: 0x%x mask: 0x%x", tap->dotted_name,
+ tap->abs_chain_position, tap->ir_length,
+ tap->ir_capture_value, tap->ir_capture_mask);
+ jtag_tap_add(tap);
+}
+
+static void jtag_tap_free(jtag_tap_t *tap)
+{
+ /// @todo is anything missing? no memory leaks please
+ free((void *)tap->expected_ids);
+ free((void *)tap->chip);
+ free((void *)tap->tapname);
+ free((void *)tap->dotted_name);
+ free(tap);
+}
+
static int jim_newtap_cmd( Jim_GetOptInfo *goi )
{
jtag_tap_t *pTap;
- jtag_tap_t **ppTap;
jim_wide w;
int x;
int e;
} /* switch(n->value) */
} /* while( goi->argc ) */
- /* Did we get all the options? */
- if( reqbits ){
- // no
- Jim_SetResult_sprintf( goi->interp,
- "newtap: %s missing required parameters",
- pTap->dotted_name);
- /* TODO: Tell user what is missing :-( */
- /* no memory leaks pelase */
- free(((void *)(pTap->expected_ids)));
- free(((void *)(pTap->chip)));
- free(((void *)(pTap->tapname)));
- free(((void *)(pTap->dotted_name)));
- free(((void *)(pTap)));
- return JIM_ERR;
- }
-
- pTap->expected = malloc( pTap->ir_length );
- pTap->expected_mask = malloc( pTap->ir_length );
- pTap->cur_instr = malloc( pTap->ir_length );
-
- buf_set_u32( pTap->expected,
- 0,
- pTap->ir_length,
- pTap->ir_capture_value );
- buf_set_u32( pTap->expected_mask,
- 0,
- pTap->ir_length,
- pTap->ir_capture_mask );
- buf_set_ones( pTap->cur_instr,
- pTap->ir_length );
-
- pTap->bypass = 1;
-
- jtag_register_event_callback(jtag_reset_callback, pTap );
-
- ppTap = &(jtag_all_taps);
- while( (*ppTap) != NULL ){
- ppTap = &((*ppTap)->next_tap);
- }
- *ppTap = pTap;
+ /* Did all the required option bits get cleared? */
+ if (0 == reqbits)
{
- static int n_taps = 0;
- pTap->abs_chain_position = n_taps++;
+ jtag_tap_init(pTap);
+ return ERROR_OK;
}
- LOG_DEBUG( "Created Tap: %s @ abs position %d, irlen %d, capture: 0x%x mask: 0x%x",
- (*ppTap)->dotted_name,
- (*ppTap)->abs_chain_position,
- (*ppTap)->ir_length,
- (*ppTap)->ir_capture_value,
- (*ppTap)->ir_capture_mask );
- return ERROR_OK;
+ Jim_SetResult_sprintf(goi->interp,
+ "newtap: %s missing required parameters",
+ pTap->dotted_name);
+ jtag_tap_free(pTap);
+ return JIM_ERR;
}
static int jim_jtag_command( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
{
jtag_tap_t *t;
- t = jtag_TapByJimObj( goi.interp, goi.argv[0] );
+ t = jtag_tap_by_jim_obj( goi.interp, goi.argv[0] );
if( t == NULL ){
return JIM_ERR;
}
jtag_tap_t *t;
Jim_GetOpt_Obj(&goi, &o);
- t = jtag_TapByJimObj( goi.interp, o );
+ t = jtag_tap_by_jim_obj( goi.interp, o );
if( t == NULL ){
return JIM_ERR;
}
jtag_tap_t *t;
Jim_GetOpt_Obj(&goi, &o);
- t = jtag_TapByJimObj( goi.interp, o );
+ t = jtag_tap_by_jim_obj( goi.interp, o );
if( t == NULL ){
return JIM_ERR;
}
}
if(hasKHz)
{
- jtag_interface->khz(speed_khz, &jtag_speed);
- hasKHz = 0;
+ jtag_interface->khz(jtag_get_speed_khz(), &jtag_speed);
+ hasKHz = false;
}
if (jtag_interface->init() != ERROR_OK)
return jtag_init_reset(cmd_ctx);
}
+void jtag_set_speed_khz(unsigned khz)
+{
+ speed_khz = khz;
+}
+unsigned jtag_get_speed_khz(void)
+{
+ return speed_khz;
+}
+
static int default_khz(int khz, int *jtag_speed)
{
LOG_ERROR("Translation from khz to jtag_speed not implemented");
newargs[0] = Jim_NewStringObj( interp, "jtag", -1 );
newargs[1] = Jim_NewStringObj( interp, "newtap", -1 );
- sprintf( buf, "chip%d", jtag_NumTotalTaps() );
+ sprintf( buf, "chip%d", jtag_tap_count() );
newargs[2] = Jim_NewStringObj( interp, buf, -1 );
- sprintf( buf, "tap%d", jtag_NumTotalTaps() );
+ sprintf( buf, "tap%d", jtag_tap_count() );
newargs[3] = Jim_NewStringObj( interp, buf, -1 );
newargs[4] = Jim_NewStringObj( interp, "-irlen", -1 );
newargs[5] = Jim_NewStringObj( interp, args[0], -1 );
{
jtag_tap_t *tap;
- tap = jtag_all_taps;
+ tap = jtag_all_taps();
command_print(cmd_ctx, " TapName | Enabled | IdCode Expected IrLen IrCap IrMask Instr ");
command_print(cmd_ctx, "---|--------------------|---------|------------|------------|------|------|------|---------");
}
else
{
- jtag_nsrst_delay = strtoul(args[0], NULL, 0);
+ jtag_set_nsrst_delay(strtoul(args[0], NULL, 0));
}
return ERROR_OK;
}
else
{
- jtag_ntrst_delay = strtoul(args[0], NULL, 0);
+ jtag_set_ntrst_delay(strtoul(args[0], NULL, 0));
}
return ERROR_OK;
}
+
static int handle_jtag_speed_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
{
int retval=ERROR_OK;
int retval=ERROR_OK;
LOG_DEBUG("handle jtag khz");
+ int cur_speed = 0;
if(argc == 1)
{
- speed_khz = strtoul(args[0], NULL, 0);
+ jtag_set_speed_khz(strtoul(args[0], NULL, 0));
if (jtag != NULL)
{
- int cur_speed = 0;
LOG_DEBUG("have interface set up");
int speed_div1;
- if ((retval=jtag->khz(speed_khz, &speed_div1))!=ERROR_OK)
+ if ((retval=jtag->khz(jtag_get_speed_khz(), &speed_div1))!=ERROR_OK)
{
- speed_khz = 0;
+ jtag_set_speed_khz(0);
return retval;
}
retval=jtag->speed(cur_speed);
} else
{
- hasKHz = 1;
+ hasKHz = true;
}
} else if (argc==0)
{
{
return ERROR_COMMAND_SYNTAX_ERROR;
}
+ cur_speed = jtag_get_speed_khz();
if (jtag!=NULL)
{
- if ((retval=jtag->speed_div(jtag_speed, &speed_khz))!=ERROR_OK)
+ if ((retval=jtag->speed_div(jtag_speed, &cur_speed))!=ERROR_OK)
return retval;
}
- if (speed_khz==0)
- {
+ if (cur_speed)
+ command_print(cmd_ctx, "%d kHz", cur_speed);
+ else
command_print(cmd_ctx, "RCLK - adaptive");
- } else
- {
- command_print(cmd_ctx, "%d kHz", speed_khz);
- }
return retval;
}
command_print( cmd_ctx, "Invalid state name: %s\n", args[0] );
return ERROR_COMMAND_SYNTAX_ERROR;
}
- jtag_add_end_state(state);
+ jtag_set_end_state(state);
jtag_execute_queue();
}
command_print(cmd_ctx, "current endstate: %s", tap_state_name(cmd_queue_end_state));
for (i = 0; i < num_fields; i++)
{
- tap = jtag_TapByString( args[i*2] );
+ tap = jtag_tap_by_string( args[i*2] );
if (tap==NULL)
{
command_print( cmd_ctx, "Tap: %s unknown", args[i*2] );
}
} /* validate args */
- tap = jtag_TapByJimObj( interp, args[1] );
+ tap = jtag_tap_by_jim_obj( interp, args[1] );
if( tap == NULL ){
return JIM_ERR;
}
static int Jim_Command_flush_count(Jim_Interp *interp, int argc, Jim_Obj *const *args)
{
- Jim_SetResult(interp, Jim_NewIntObj(interp, jtag_flush_queue_count));
+ Jim_SetResult(interp, Jim_NewIntObj(interp, jtag_get_flush_queue_count()));
return JIM_OK;
}
return ERROR_OK;
}
+void jtag_set_verify(bool enable)
+{
+ jtag_verify = enable;
+}
+
+bool jtag_will_verify()
+{
+ return jtag_verify;
+}
+
static int handle_verify_jtag_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
{
+ if (argc > 1)
+ return ERROR_COMMAND_SYNTAX_ERROR;
+
if (argc == 1)
{
if (strcmp(args[0], "enable") == 0)
- {
- jtag_verify = 1;
- }
+ jtag_set_verify(true);
else if (strcmp(args[0], "disable") == 0)
- {
- jtag_verify = 0;
- } else
- {
+ jtag_set_verify(false);
+ else
return ERROR_COMMAND_SYNTAX_ERROR;
- }
- } else if (argc != 0)
- {
- return ERROR_COMMAND_SYNTAX_ERROR;
}
- command_print(cmd_ctx, "verify jtag capture is %s", (jtag_verify) ? "enabled": "disabled");
+ const char *status = jtag_will_verify() ? "enabled": "disabled";
+ command_print(cmd_ctx, "verify jtag capture is %s", status);
return ERROR_OK;
}
return retval;
}
+void jtag_set_nsrst_delay(unsigned delay)
+{
+ jtag_nsrst_delay = delay;
+}
+void jtag_set_ntrst_delay(unsigned delay)
+{
+ jtag_ntrst_delay = delay;
+}
+
+