1 /* SPDX-License-Identifier: GPL-2.0-or-later */
3 * Copyright (C) 2005 by Dominic Rath <Dominic.Rath@gmx.de>
4 * Copyright (C) 2007-2010 Øyvind Harboe <oyvind.harboe@zylin.com>
5 * Copyright (C) 2009 SoftPLC Corporation, http://softplc.com, Dick Hollenbeck <dick@softplc.com>
6 * Copyright (C) 2009 Zachary T Welch <zw@superlucidity.net>
7 * Copyright (C) 2018 Pengutronix, Oleksij Rempel <kernel@pengutronix.de>
16 #include "minidriver.h"
17 #include "interface.h"
18 #include "interfaces.h"
19 #include <transport/transport.h>
27 * Holds support for configuring debug adapters from TCl scripts.
30 struct adapter_driver
*adapter_driver
;
31 const char * const jtag_only
[] = { "jtag", NULL
};
34 * Adapter configuration
42 * 2 * 7 chars: max 7 ports
43 * 1 char: test for overflow
47 #define USB_MAX_LOCATION_LENGTH 16
49 #ifdef HAVE_LIBUSB_GET_PORT_NUMBERS
50 static void adapter_usb_set_location(const char *location
)
52 if (strnlen(location
, USB_MAX_LOCATION_LENGTH
) == USB_MAX_LOCATION_LENGTH
)
53 LOG_WARNING("usb location string is too long!!");
55 free(adapter_config
.usb_location
);
57 adapter_config
.usb_location
= strndup(location
, USB_MAX_LOCATION_LENGTH
);
59 #endif /* HAVE_LIBUSB_GET_PORT_NUMBERS */
61 const char *adapter_usb_get_location(void)
63 return adapter_config
.usb_location
;
66 bool adapter_usb_location_equal(uint8_t dev_bus
, uint8_t *port_path
, size_t path_len
)
68 size_t path_step
, string_length
;
72 if (!adapter_usb_get_location())
75 /* strtok need non const char */
76 loc
= strndup(adapter_usb_get_location(), USB_MAX_LOCATION_LENGTH
);
77 string_length
= strnlen(loc
, USB_MAX_LOCATION_LENGTH
);
79 ptr
= strtok(loc
, "-");
81 LOG_WARNING("no '-' in usb path\n");
85 string_length
-= strnlen(ptr
, string_length
);
86 /* check bus mismatch */
87 if (atoi(ptr
) != dev_bus
)
91 while (path_step
< path_len
) {
92 ptr
= strtok(NULL
, ".");
94 /* no more tokens in path */
98 /* path mismatch at some step */
99 if (path_step
< path_len
&& atoi(ptr
) != port_path
[path_step
])
103 string_length
-= strnlen(ptr
, string_length
) + 1;
106 /* walked the full path, all elements match */
107 if (path_step
== path_len
&& !string_length
)
115 static int jim_adapter_name(Jim_Interp
*interp
, int argc
, Jim_Obj
* const *argv
)
117 struct jim_getopt_info goi
;
118 jim_getopt_setup(&goi
, interp
, argc
-1, argv
+ 1);
120 /* return the name of the interface */
121 /* TCL code might need to know the exact type... */
122 /* FUTURE: we allow this as a means to "set" the interface. */
124 Jim_WrongNumArgs(goi
.interp
, 1, goi
.argv
-1, "(no params)");
127 const char *name
= adapter_driver
? adapter_driver
->name
: NULL
;
128 Jim_SetResultString(goi
.interp
, name
? name
: "undefined", -1);
132 COMMAND_HANDLER(adapter_transports_command
)
137 retval
= CALL_COMMAND_HANDLER(transport_list_parse
, &transports
);
138 if (retval
!= ERROR_OK
)
141 retval
= allow_transports(CMD_CTX
, (const char **)transports
);
143 if (retval
!= ERROR_OK
) {
144 for (unsigned i
= 0; transports
[i
]; i
++)
151 COMMAND_HANDLER(handle_adapter_list_command
)
153 if (strcmp(CMD_NAME
, "list") == 0 && CMD_ARGC
> 0)
154 return ERROR_COMMAND_SYNTAX_ERROR
;
156 command_print(CMD
, "The following debug adapters are available:");
157 for (unsigned i
= 0; adapter_drivers
[i
]; i
++) {
158 const char *name
= adapter_drivers
[i
]->name
;
159 command_print(CMD
, "%u: %s", i
+ 1, name
);
165 COMMAND_HANDLER(handle_adapter_driver_command
)
169 /* check whether the interface is already configured */
170 if (adapter_driver
) {
171 LOG_WARNING("Interface already configured, ignoring");
175 /* interface name is a mandatory argument */
176 if (CMD_ARGC
!= 1 || CMD_ARGV
[0][0] == '\0')
177 return ERROR_COMMAND_SYNTAX_ERROR
;
179 for (unsigned i
= 0; adapter_drivers
[i
]; i
++) {
180 if (strcmp(CMD_ARGV
[0], adapter_drivers
[i
]->name
) != 0)
183 if (adapter_drivers
[i
]->commands
) {
184 retval
= register_commands(CMD_CTX
, NULL
,
185 adapter_drivers
[i
]->commands
);
186 if (retval
!= ERROR_OK
)
190 adapter_driver
= adapter_drivers
[i
];
192 return allow_transports(CMD_CTX
, adapter_driver
->transports
);
195 /* no valid interface was found (i.e. the configuration option,
196 * didn't match one of the compiled-in interfaces
198 LOG_ERROR("The specified debug interface was not found (%s)",
200 CALL_COMMAND_HANDLER(handle_adapter_list_command
);
201 return ERROR_JTAG_INVALID_INTERFACE
;
204 COMMAND_HANDLER(handle_reset_config_command
)
209 /* Original versions cared about the order of these tokens:
210 * reset_config signals [combination [trst_type [srst_type]]]
211 * They also clobbered the previous configuration even on error.
213 * Here we don't care about the order, and only change values
214 * which have been explicitly specified.
216 for (; CMD_ARGC
; CMD_ARGC
--, CMD_ARGV
++) {
221 m
= RESET_SRST_NO_GATING
;
222 if (strcmp(*CMD_ARGV
, "srst_gates_jtag") == 0)
223 /* default: don't use JTAG while SRST asserted */;
224 else if (strcmp(*CMD_ARGV
, "srst_nogate") == 0)
225 tmp
= RESET_SRST_NO_GATING
;
229 LOG_ERROR("extra reset_config %s spec (%s)",
230 "gating", *CMD_ARGV
);
231 return ERROR_COMMAND_SYNTAX_ERROR
;
237 m
= RESET_HAS_TRST
| RESET_HAS_SRST
;
238 if (strcmp(*CMD_ARGV
, "none") == 0)
240 else if (strcmp(*CMD_ARGV
, "trst_only") == 0)
241 tmp
= RESET_HAS_TRST
;
242 else if (strcmp(*CMD_ARGV
, "srst_only") == 0)
243 tmp
= RESET_HAS_SRST
;
244 else if (strcmp(*CMD_ARGV
, "trst_and_srst") == 0)
245 tmp
= RESET_HAS_TRST
| RESET_HAS_SRST
;
249 LOG_ERROR("extra reset_config %s spec (%s)",
250 "signal", *CMD_ARGV
);
251 return ERROR_COMMAND_SYNTAX_ERROR
;
256 /* combination (options for broken wiring) */
257 m
= RESET_SRST_PULLS_TRST
| RESET_TRST_PULLS_SRST
;
258 if (strcmp(*CMD_ARGV
, "separate") == 0)
259 /* separate reset lines - default */;
260 else if (strcmp(*CMD_ARGV
, "srst_pulls_trst") == 0)
261 tmp
|= RESET_SRST_PULLS_TRST
;
262 else if (strcmp(*CMD_ARGV
, "trst_pulls_srst") == 0)
263 tmp
|= RESET_TRST_PULLS_SRST
;
264 else if (strcmp(*CMD_ARGV
, "combined") == 0)
265 tmp
|= RESET_SRST_PULLS_TRST
| RESET_TRST_PULLS_SRST
;
269 LOG_ERROR("extra reset_config %s spec (%s)",
270 "combination", *CMD_ARGV
);
271 return ERROR_COMMAND_SYNTAX_ERROR
;
276 /* trst_type (NOP without HAS_TRST) */
277 m
= RESET_TRST_OPEN_DRAIN
;
278 if (strcmp(*CMD_ARGV
, "trst_open_drain") == 0)
279 tmp
|= RESET_TRST_OPEN_DRAIN
;
280 else if (strcmp(*CMD_ARGV
, "trst_push_pull") == 0)
281 /* push/pull from adapter - default */;
285 LOG_ERROR("extra reset_config %s spec (%s)",
286 "trst_type", *CMD_ARGV
);
287 return ERROR_COMMAND_SYNTAX_ERROR
;
292 /* srst_type (NOP without HAS_SRST) */
293 m
= RESET_SRST_PUSH_PULL
;
294 if (strcmp(*CMD_ARGV
, "srst_push_pull") == 0)
295 tmp
|= RESET_SRST_PUSH_PULL
;
296 else if (strcmp(*CMD_ARGV
, "srst_open_drain") == 0)
297 /* open drain from adapter - default */;
301 LOG_ERROR("extra reset_config %s spec (%s)",
302 "srst_type", *CMD_ARGV
);
303 return ERROR_COMMAND_SYNTAX_ERROR
;
308 /* connect_type - only valid when srst_nogate */
309 m
= RESET_CNCT_UNDER_SRST
;
310 if (strcmp(*CMD_ARGV
, "connect_assert_srst") == 0)
311 tmp
|= RESET_CNCT_UNDER_SRST
;
312 else if (strcmp(*CMD_ARGV
, "connect_deassert_srst") == 0)
313 /* connect normally - default */;
317 LOG_ERROR("extra reset_config %s spec (%s)",
318 "connect_type", *CMD_ARGV
);
319 return ERROR_COMMAND_SYNTAX_ERROR
;
324 /* caller provided nonsense; fail */
325 LOG_ERROR("unknown reset_config flag (%s)", *CMD_ARGV
);
326 return ERROR_COMMAND_SYNTAX_ERROR
;
329 /* Remember the bits which were specified (mask)
330 * and their new values (new_cfg).
336 /* clear previous values of those bits, save new values */
338 int old_cfg
= jtag_get_reset_config();
342 jtag_set_reset_config(new_cfg
);
344 new_cfg
= jtag_get_reset_config();
347 * Display the (now-)current reset mode
351 /* minimal JTAG has neither SRST nor TRST (so that's the default) */
352 switch (new_cfg
& (RESET_HAS_TRST
| RESET_HAS_SRST
)) {
354 modes
[0] = "srst_only";
357 modes
[0] = "trst_only";
359 case RESET_TRST_AND_SRST
:
360 modes
[0] = "trst_and_srst";
367 /* normally SRST and TRST are decoupled; but bugs happen ... */
368 switch (new_cfg
& (RESET_SRST_PULLS_TRST
| RESET_TRST_PULLS_SRST
)) {
369 case RESET_SRST_PULLS_TRST
:
370 modes
[1] = "srst_pulls_trst";
372 case RESET_TRST_PULLS_SRST
:
373 modes
[1] = "trst_pulls_srst";
375 case RESET_SRST_PULLS_TRST
| RESET_TRST_PULLS_SRST
:
376 modes
[1] = "combined";
379 modes
[1] = "separate";
383 /* TRST-less connectors include Altera, Xilinx, and minimal JTAG */
384 if (new_cfg
& RESET_HAS_TRST
) {
385 if (new_cfg
& RESET_TRST_OPEN_DRAIN
)
386 modes
[3] = " trst_open_drain";
388 modes
[3] = " trst_push_pull";
392 /* SRST-less connectors include TI-14, Xilinx, and minimal JTAG */
393 if (new_cfg
& RESET_HAS_SRST
) {
394 if (new_cfg
& RESET_SRST_NO_GATING
)
395 modes
[2] = " srst_nogate";
397 modes
[2] = " srst_gates_jtag";
399 if (new_cfg
& RESET_SRST_PUSH_PULL
)
400 modes
[4] = " srst_push_pull";
402 modes
[4] = " srst_open_drain";
404 if (new_cfg
& RESET_CNCT_UNDER_SRST
)
405 modes
[5] = " connect_assert_srst";
407 modes
[5] = " connect_deassert_srst";
414 command_print(CMD
, "%s %s%s%s%s%s",
416 modes
[2], modes
[3], modes
[4], modes
[5]);
421 COMMAND_HANDLER(handle_adapter_srst_delay_command
)
424 return ERROR_COMMAND_SYNTAX_ERROR
;
427 COMMAND_PARSE_NUMBER(uint
, CMD_ARGV
[0], delay
);
429 jtag_set_nsrst_delay(delay
);
431 command_print(CMD
, "adapter srst delay: %u", jtag_get_nsrst_delay());
435 COMMAND_HANDLER(handle_adapter_srst_pulse_width_command
)
438 return ERROR_COMMAND_SYNTAX_ERROR
;
441 COMMAND_PARSE_NUMBER(uint
, CMD_ARGV
[0], width
);
443 jtag_set_nsrst_assert_width(width
);
445 command_print(CMD
, "adapter srst pulse_width: %u", jtag_get_nsrst_assert_width());
449 COMMAND_HANDLER(handle_adapter_speed_command
)
452 return ERROR_COMMAND_SYNTAX_ERROR
;
454 int retval
= ERROR_OK
;
457 COMMAND_PARSE_NUMBER(uint
, CMD_ARGV
[0], khz
);
459 retval
= jtag_config_khz(khz
);
460 if (retval
!= ERROR_OK
)
464 int cur_speed
= jtag_get_speed_khz();
465 retval
= jtag_get_speed_readable(&cur_speed
);
466 if (retval
!= ERROR_OK
)
470 command_print(CMD
, "adapter speed: %d kHz", cur_speed
);
472 command_print(CMD
, "adapter speed: RCLK - adaptive");
477 COMMAND_HANDLER(handle_adapter_reset_de_assert
)
480 VALUE_UNDEFINED
= -1,
485 enum values srst
= VALUE_UNDEFINED
;
486 enum values trst
= VALUE_UNDEFINED
;
487 enum reset_types jtag_reset_config
= jtag_get_reset_config();
491 if (transport_is_jtag()) {
492 if (jtag_reset_config
& RESET_HAS_TRST
)
493 signal
= jtag_get_trst() ? "asserted" : "deasserted";
495 signal
= "not present";
496 command_print(CMD
, "trst %s", signal
);
499 if (jtag_reset_config
& RESET_HAS_SRST
)
500 signal
= jtag_get_srst() ? "asserted" : "deasserted";
502 signal
= "not present";
503 command_print(CMD
, "srst %s", signal
);
508 if (CMD_ARGC
!= 1 && CMD_ARGC
!= 3)
509 return ERROR_COMMAND_SYNTAX_ERROR
;
511 value
= (strcmp(CMD_NAME
, "assert") == 0) ? VALUE_ASSERT
: VALUE_DEASSERT
;
512 if (strcmp(CMD_ARGV
[0], "srst") == 0)
514 else if (strcmp(CMD_ARGV
[0], "trst") == 0)
517 return ERROR_COMMAND_SYNTAX_ERROR
;
520 if (strcmp(CMD_ARGV
[1], "assert") == 0)
521 value
= VALUE_ASSERT
;
522 else if (strcmp(CMD_ARGV
[1], "deassert") == 0)
523 value
= VALUE_DEASSERT
;
525 return ERROR_COMMAND_SYNTAX_ERROR
;
527 if (strcmp(CMD_ARGV
[2], "srst") == 0 && srst
== VALUE_UNDEFINED
)
529 else if (strcmp(CMD_ARGV
[2], "trst") == 0 && trst
== VALUE_UNDEFINED
)
532 return ERROR_COMMAND_SYNTAX_ERROR
;
535 if (trst
== VALUE_UNDEFINED
) {
536 if (transport_is_jtag())
537 trst
= jtag_get_trst() ? VALUE_ASSERT
: VALUE_DEASSERT
;
539 trst
= VALUE_DEASSERT
; /* unused, safe value */
542 if (srst
== VALUE_UNDEFINED
) {
543 if (jtag_reset_config
& RESET_HAS_SRST
)
544 srst
= jtag_get_srst() ? VALUE_ASSERT
: VALUE_DEASSERT
;
546 srst
= VALUE_DEASSERT
; /* unused, safe value */
549 if (trst
== VALUE_ASSERT
&& !transport_is_jtag()) {
550 LOG_ERROR("transport has no trst signal");
554 if (srst
== VALUE_ASSERT
&& !(jtag_reset_config
& RESET_HAS_SRST
)) {
555 LOG_ERROR("adapter has no srst signal");
559 return adapter_resets((trst
== VALUE_DEASSERT
) ? TRST_DEASSERT
: TRST_ASSERT
,
560 (srst
== VALUE_DEASSERT
) ? SRST_DEASSERT
: SRST_ASSERT
);
563 #ifdef HAVE_LIBUSB_GET_PORT_NUMBERS
564 COMMAND_HANDLER(handle_usb_location_command
)
567 adapter_usb_set_location(CMD_ARGV
[0]);
569 command_print(CMD
, "adapter usb location: %s", adapter_usb_get_location());
573 #endif /* HAVE_LIBUSB_GET_PORT_NUMBERS */
575 static const struct command_registration adapter_usb_command_handlers
[] = {
576 #ifdef HAVE_LIBUSB_GET_PORT_NUMBERS
579 .handler
= &handle_usb_location_command
,
580 .mode
= COMMAND_CONFIG
,
581 .help
= "display or set the USB bus location of the USB device",
582 .usage
= "[<bus>-port[.port]...]",
584 #endif /* HAVE_LIBUSB_GET_PORT_NUMBERS */
585 COMMAND_REGISTRATION_DONE
588 static const struct command_registration adapter_srst_command_handlers
[] = {
591 .handler
= handle_adapter_srst_delay_command
,
593 .help
= "delay after deasserting SRST in ms",
594 .usage
= "[milliseconds]",
597 .name
= "pulse_width",
598 .handler
= handle_adapter_srst_pulse_width_command
,
600 .help
= "SRST assertion pulse width in ms",
601 .usage
= "[milliseconds]",
603 COMMAND_REGISTRATION_DONE
606 static const struct command_registration adapter_command_handlers
[] = {
609 .handler
= handle_adapter_driver_command
,
610 .mode
= COMMAND_CONFIG
,
611 .help
= "Select a debug adapter driver",
612 .usage
= "driver_name",
616 .handler
= handle_adapter_speed_command
,
618 .help
= "With an argument, change to the specified maximum "
619 "jtag speed. For JTAG, 0 KHz signifies adaptive "
621 "With or without argument, display current setting.",
626 .handler
= handle_adapter_list_command
,
628 .help
= "List all built-in debug adapter drivers",
634 .jim_handler
= jim_adapter_name
,
635 .help
= "Returns the name of the currently "
636 "selected adapter (driver)",
641 .help
= "srst adapter command group",
643 .chain
= adapter_srst_command_handlers
,
646 .name
= "transports",
647 .handler
= adapter_transports_command
,
648 .mode
= COMMAND_CONFIG
,
649 .help
= "Declare transports the adapter supports.",
650 .usage
= "transport ...",
655 .help
= "usb adapter command group",
657 .chain
= adapter_usb_command_handlers
,
661 .handler
= handle_adapter_reset_de_assert
,
662 .mode
= COMMAND_EXEC
,
663 .help
= "Controls SRST and TRST lines.",
664 .usage
= "|deassert [srst|trst [assert|deassert srst|trst]]",
668 .handler
= handle_adapter_reset_de_assert
,
669 .mode
= COMMAND_EXEC
,
670 .help
= "Controls SRST and TRST lines.",
671 .usage
= "|assert [srst|trst [deassert|assert srst|trst]]",
673 COMMAND_REGISTRATION_DONE
676 static const struct command_registration interface_command_handlers
[] = {
680 .help
= "adapter command group",
682 .chain
= adapter_command_handlers
,
685 .name
= "reset_config",
686 .handler
= handle_reset_config_command
,
688 .help
= "configure adapter reset behavior",
689 .usage
= "[none|trst_only|srst_only|trst_and_srst] "
690 "[srst_pulls_trst|trst_pulls_srst|combined|separate] "
691 "[srst_gates_jtag|srst_nogate] "
692 "[trst_push_pull|trst_open_drain] "
693 "[srst_push_pull|srst_open_drain] "
694 "[connect_deassert_srst|connect_assert_srst]",
696 COMMAND_REGISTRATION_DONE
700 * Register the commands which deal with arbitrary debug adapter drivers.
702 * @todo Remove internal assumptions that all debug adapters use JTAG for
703 * transport. Various types and data structures are not named generically.
705 int interface_register_commands(struct command_context
*ctx
)
707 return register_commands(ctx
, NULL
, interface_command_handlers
);
Linking to existing account procedure
If you already have an account and want to add another login method
you
MUST first sign in with your existing account and
then change URL to read
https://review.openocd.org/login/?link
to get to this page again but this time it'll work for linking. Thank you.
SSH host keys fingerprints
1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=.. |
|+o.. . |
|*.o . . |
|+B . . . |
|Bo. = o S |
|Oo.+ + = |
|oB=.* = . o |
| =+=.+ + E |
|. .=o . o |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)