1 /***************************************************************************
2 * Copyright (C) 2005 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
24 #include "replacements.h"
28 #include "configuration.h"
29 #include "binarybuffer.h"
35 #include <sys/types.h>
43 #include <time_support.h>
47 int cli_target_callback_event_handler(struct target_s
*target
, enum target_event event
, void *priv
);
49 int handle_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
50 int handle_daemon_startup_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
51 int handle_targets_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
53 int handle_target_script_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
54 int handle_run_and_halt_time_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
55 int handle_working_area_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
57 int handle_reg_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
58 int handle_poll_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
59 int handle_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
60 int handle_wait_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
61 int handle_reset_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
62 int handle_soft_reset_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
63 int handle_resume_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
64 int handle_step_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
65 int handle_md_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
66 int handle_mw_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
67 int handle_load_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
68 int handle_dump_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
69 int handle_bp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
70 int handle_rbp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
71 int handle_wp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
72 int handle_rwp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
76 extern target_type_t arm7tdmi_target
;
77 extern target_type_t arm720t_target
;
78 extern target_type_t arm9tdmi_target
;
79 extern target_type_t arm920t_target
;
80 extern target_type_t arm966e_target
;
81 extern target_type_t arm926ejs_target
;
82 extern target_type_t xscale_target
;
84 target_type_t
*target_types
[] =
96 target_t
*targets
= NULL
;
97 target_event_callback_t
*target_event_callbacks
= NULL
;
98 target_timer_callback_t
*target_timer_callbacks
= NULL
;
100 char *target_state_strings
[] =
109 char *target_debug_reason_strings
[] =
111 "debug request", "breakpoint", "watchpoint",
112 "watchpoint and breakpoint", "single step",
116 char *target_endianess_strings
[] =
122 enum daemon_startup_mode startup_mode
= DAEMON_ATTACH
;
124 static int target_continous_poll
= 1;
126 /* read a u32 from a buffer in target memory endianness */
127 u32
target_buffer_get_u32(target_t
*target
, u8
*buffer
)
129 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
130 return le_to_h_u32(buffer
);
132 return be_to_h_u32(buffer
);
135 /* read a u16 from a buffer in target memory endianness */
136 u16
target_buffer_get_u16(target_t
*target
, u8
*buffer
)
138 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
139 return le_to_h_u16(buffer
);
141 return be_to_h_u16(buffer
);
144 /* write a u32 to a buffer in target memory endianness */
145 void target_buffer_set_u32(target_t
*target
, u8
*buffer
, u32 value
)
147 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
148 h_u32_to_le(buffer
, value
);
150 h_u32_to_be(buffer
, value
);
153 /* write a u16 to a buffer in target memory endianness */
154 void target_buffer_set_u16(target_t
*target
, u8
*buffer
, u16 value
)
156 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
157 h_u16_to_le(buffer
, value
);
159 h_u16_to_be(buffer
, value
);
162 /* returns a pointer to the n-th configured target */
163 target_t
* get_target_by_num(int num
)
165 target_t
*target
= targets
;
172 target
= target
->next
;
179 int get_num_by_target(target_t
*query_target
)
181 target_t
*target
= targets
;
186 if (target
== query_target
)
188 target
= target
->next
;
195 target_t
* get_current_target(command_context_t
*cmd_ctx
)
197 target_t
*target
= get_target_by_num(cmd_ctx
->current_target
);
201 ERROR("BUG: current_target out of bounds");
208 /* Process target initialization, when target entered debug out of reset
209 * the handler is unregistered at the end of this function, so it's only called once
211 int target_init_handler(struct target_s
*target
, enum target_event event
, void *priv
)
214 struct command_context_s
*cmd_ctx
= priv
;
216 if ((event
== TARGET_EVENT_HALTED
) && (target
->reset_script
))
218 target_unregister_event_callback(target_init_handler
, priv
);
220 script
= fopen(target
->reset_script
, "r");
223 ERROR("couldn't open script file %s", target
->reset_script
);
227 INFO("executing reset script '%s'", target
->reset_script
);
228 command_run_file(cmd_ctx
, script
, COMMAND_EXEC
);
231 jtag_execute_queue();
237 int target_run_and_halt_handler(void *priv
)
239 target_t
*target
= priv
;
241 target
->type
->halt(target
);
246 int target_process_reset(struct command_context_s
*cmd_ctx
)
248 int retval
= ERROR_OK
;
254 target
->type
->assert_reset(target
);
255 target
= target
->next
;
257 jtag_execute_queue();
259 /* request target halt if necessary, and schedule further action */
263 switch (target
->reset_mode
)
266 /* nothing to do if target just wants to be run */
268 case RESET_RUN_AND_HALT
:
270 target_register_timer_callback(target_run_and_halt_handler
, target
->run_and_halt_time
, 0, target
);
272 case RESET_RUN_AND_INIT
:
274 target_register_timer_callback(target_run_and_halt_handler
, target
->run_and_halt_time
, 0, target
);
275 target_register_event_callback(target_init_handler
, cmd_ctx
);
278 target
->type
->halt(target
);
281 target
->type
->halt(target
);
282 target_register_event_callback(target_init_handler
, cmd_ctx
);
285 ERROR("BUG: unknown target->reset_mode");
287 target
= target
->next
;
293 target
->type
->deassert_reset(target
);
294 target
= target
->next
;
296 jtag_execute_queue();
301 int target_init(struct command_context_s
*cmd_ctx
)
303 target_t
*target
= targets
;
307 if (target
->type
->init_target(cmd_ctx
, target
) != ERROR_OK
)
309 ERROR("target '%s' init failed", target
->type
->name
);
312 target
= target
->next
;
317 target_register_user_commands(cmd_ctx
);
318 target_register_timer_callback(handle_target
, 100, 1, NULL
);
321 if (startup_mode
== DAEMON_RESET
)
322 target_process_reset(cmd_ctx
);
327 int target_register_event_callback(int (*callback
)(struct target_s
*target
, enum target_event event
, void *priv
), void *priv
)
329 target_event_callback_t
**callbacks_p
= &target_event_callbacks
;
331 if (callback
== NULL
)
333 return ERROR_INVALID_ARGUMENTS
;
338 while ((*callbacks_p
)->next
)
339 callbacks_p
= &((*callbacks_p
)->next
);
340 callbacks_p
= &((*callbacks_p
)->next
);
343 (*callbacks_p
) = malloc(sizeof(target_event_callback_t
));
344 (*callbacks_p
)->callback
= callback
;
345 (*callbacks_p
)->priv
= priv
;
346 (*callbacks_p
)->next
= NULL
;
351 int target_register_timer_callback(int (*callback
)(void *priv
), int time_ms
, int periodic
, void *priv
)
353 target_timer_callback_t
**callbacks_p
= &target_timer_callbacks
;
356 if (callback
== NULL
)
358 return ERROR_INVALID_ARGUMENTS
;
363 while ((*callbacks_p
)->next
)
364 callbacks_p
= &((*callbacks_p
)->next
);
365 callbacks_p
= &((*callbacks_p
)->next
);
368 (*callbacks_p
) = malloc(sizeof(target_timer_callback_t
));
369 (*callbacks_p
)->callback
= callback
;
370 (*callbacks_p
)->periodic
= periodic
;
371 (*callbacks_p
)->time_ms
= time_ms
;
373 gettimeofday(&now
, NULL
);
374 (*callbacks_p
)->when
.tv_usec
= now
.tv_usec
+ (time_ms
% 1000) * 1000;
375 time_ms
-= (time_ms
% 1000);
376 (*callbacks_p
)->when
.tv_sec
= now
.tv_sec
+ (time_ms
/ 1000);
377 if ((*callbacks_p
)->when
.tv_usec
> 1000000)
379 (*callbacks_p
)->when
.tv_usec
= (*callbacks_p
)->when
.tv_usec
- 1000000;
380 (*callbacks_p
)->when
.tv_sec
+= 1;
383 (*callbacks_p
)->priv
= priv
;
384 (*callbacks_p
)->next
= NULL
;
389 int target_unregister_event_callback(int (*callback
)(struct target_s
*target
, enum target_event event
, void *priv
), void *priv
)
391 target_event_callback_t
**p
= &target_event_callbacks
;
392 target_event_callback_t
*c
= target_event_callbacks
;
394 if (callback
== NULL
)
396 return ERROR_INVALID_ARGUMENTS
;
401 target_event_callback_t
*next
= c
->next
;
402 if ((c
->callback
== callback
) && (c
->priv
== priv
))
416 int target_unregister_timer_callback(int (*callback
)(void *priv
), void *priv
)
418 target_timer_callback_t
**p
= &target_timer_callbacks
;
419 target_timer_callback_t
*c
= target_timer_callbacks
;
421 if (callback
== NULL
)
423 return ERROR_INVALID_ARGUMENTS
;
428 target_timer_callback_t
*next
= c
->next
;
429 if ((c
->callback
== callback
) && (c
->priv
== priv
))
443 int target_call_event_callbacks(target_t
*target
, enum target_event event
)
445 target_event_callback_t
*callback
= target_event_callbacks
;
446 target_event_callback_t
*next_callback
;
448 DEBUG("target event %i", event
);
452 next_callback
= callback
->next
;
453 callback
->callback(target
, event
, callback
->priv
);
454 callback
= next_callback
;
460 int target_call_timer_callbacks()
462 target_timer_callback_t
*callback
= target_timer_callbacks
;
463 target_timer_callback_t
*next_callback
;
466 gettimeofday(&now
, NULL
);
470 next_callback
= callback
->next
;
472 if (((now
.tv_sec
>= callback
->when
.tv_sec
) && (now
.tv_usec
>= callback
->when
.tv_usec
))
473 || (now
.tv_sec
> callback
->when
.tv_sec
))
475 callback
->callback(callback
->priv
);
476 if (callback
->periodic
)
478 int time_ms
= callback
->time_ms
;
479 callback
->when
.tv_usec
= now
.tv_usec
+ (time_ms
% 1000) * 1000;
480 time_ms
-= (time_ms
% 1000);
481 callback
->when
.tv_sec
= now
.tv_sec
+ time_ms
/ 1000;
482 if (callback
->when
.tv_usec
> 1000000)
484 callback
->when
.tv_usec
= callback
->when
.tv_usec
- 1000000;
485 callback
->when
.tv_sec
+= 1;
489 target_unregister_timer_callback(callback
->callback
, callback
->priv
);
492 callback
= next_callback
;
498 int target_alloc_working_area(struct target_s
*target
, u32 size
, working_area_t
**area
)
500 working_area_t
*c
= target
->working_areas
;
501 working_area_t
*new_wa
= NULL
;
503 /* only allocate multiples of 4 byte */
506 ERROR("BUG: code tried to allocate unaligned number of bytes, padding");
507 size
= CEIL(size
, 4);
510 /* see if there's already a matching working area */
513 if ((c
->free
) && (c
->size
== size
))
521 /* if not, allocate a new one */
524 working_area_t
**p
= &target
->working_areas
;
525 u32 first_free
= target
->working_area
;
526 u32 free_size
= target
->working_area_size
;
528 DEBUG("allocating new working area");
530 c
= target
->working_areas
;
533 first_free
+= c
->size
;
534 free_size
-= c
->size
;
539 if (free_size
< size
)
541 WARNING("not enough working area available");
542 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
545 new_wa
= malloc(sizeof(working_area_t
));
548 new_wa
->address
= first_free
;
550 if (target
->backup_working_area
)
552 new_wa
->backup
= malloc(new_wa
->size
);
553 target
->type
->read_memory(target
, new_wa
->address
, 4, new_wa
->size
/ 4, new_wa
->backup
);
557 new_wa
->backup
= NULL
;
560 /* put new entry in list */
564 /* mark as used, and return the new (reused) area */
574 int target_free_working_area(struct target_s
*target
, working_area_t
*area
)
579 if (target
->backup_working_area
)
580 target
->type
->write_memory(target
, area
->address
, 4, area
->size
/ 4, area
->backup
);
584 /* mark user pointer invalid */
591 int target_free_all_working_areas(struct target_s
*target
)
593 working_area_t
*c
= target
->working_areas
;
597 working_area_t
*next
= c
->next
;
598 target_free_working_area(target
, c
);
608 target
->working_areas
= NULL
;
613 int target_register_commands(struct command_context_s
*cmd_ctx
)
615 register_command(cmd_ctx
, NULL
, "target", handle_target_command
, COMMAND_CONFIG
, NULL
);
616 register_command(cmd_ctx
, NULL
, "targets", handle_targets_command
, COMMAND_EXEC
, NULL
);
617 register_command(cmd_ctx
, NULL
, "daemon_startup", handle_daemon_startup_command
, COMMAND_CONFIG
, NULL
);
618 register_command(cmd_ctx
, NULL
, "target_script", handle_target_script_command
, COMMAND_CONFIG
, NULL
);
619 register_command(cmd_ctx
, NULL
, "run_and_halt_time", handle_run_and_halt_time_command
, COMMAND_CONFIG
, NULL
);
620 register_command(cmd_ctx
, NULL
, "working_area", handle_working_area_command
, COMMAND_CONFIG
, NULL
);
625 int target_write_buffer(struct target_s
*target
, u32 address
, u32 size
, u8
*buffer
)
629 DEBUG("writing buffer of %i byte at 0x%8.8x", size
, address
);
631 /* handle writes of less than 4 byte */
634 if ((retval
= target
->type
->write_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
638 /* handle unaligned head bytes */
641 int unaligned
= 4 - (address
% 4);
643 if ((retval
= target
->type
->write_memory(target
, address
, 1, unaligned
, buffer
)) != ERROR_OK
)
647 address
+= unaligned
;
651 /* handle aligned words */
654 int aligned
= size
- (size
% 4);
656 /* use bulk writes above a certain limit. This may have to be changed */
659 if ((retval
= target
->type
->bulk_write_memory(target
, address
, aligned
/ 4, buffer
)) != ERROR_OK
)
664 if ((retval
= target
->type
->write_memory(target
, address
, 4, aligned
/ 4, buffer
)) != ERROR_OK
)
673 /* handle tail writes of less than 4 bytes */
676 if ((retval
= target
->type
->write_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
683 int target_read_buffer(struct target_s
*target
, u32 address
, u32 size
, u8
*buffer
)
687 DEBUG("reading buffer of %i byte at 0x%8.8x", size
, address
);
689 /* handle reads of less than 4 byte */
692 if ((retval
= target
->type
->read_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
696 /* handle unaligned head bytes */
699 int unaligned
= 4 - (address
% 4);
701 if ((retval
= target
->type
->read_memory(target
, address
, 1, unaligned
, buffer
)) != ERROR_OK
)
705 address
+= unaligned
;
709 /* handle aligned words */
712 int aligned
= size
- (size
% 4);
714 if ((retval
= target
->type
->read_memory(target
, address
, 4, aligned
/ 4, buffer
)) != ERROR_OK
)
722 /* handle tail writes of less than 4 bytes */
725 if ((retval
= target
->type
->read_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
732 int target_read_u32(struct target_s
*target
, u32 address
, u32
*value
)
736 int retval
= target
->type
->read_memory(target
, address
, 4, 1, value_buf
);
738 if (retval
== ERROR_OK
)
740 *value
= target_buffer_get_u32(target
, value_buf
);
741 DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, *value
);
746 DEBUG("address: 0x%8.8x failed", address
);
752 int target_read_u16(struct target_s
*target
, u32 address
, u16
*value
)
756 int retval
= target
->type
->read_memory(target
, address
, 2, 1, value_buf
);
758 if (retval
== ERROR_OK
)
760 *value
= target_buffer_get_u16(target
, value_buf
);
761 DEBUG("address: 0x%8.8x, value: 0x%4.4x", address
, *value
);
766 DEBUG("address: 0x%8.8x failed", address
);
772 int target_read_u8(struct target_s
*target
, u32 address
, u8
*value
)
774 int retval
= target
->type
->read_memory(target
, address
, 1, 1, value
);
776 if (retval
== ERROR_OK
)
778 DEBUG("address: 0x%8.8x, value: 0x%2.2x", address
, *value
);
783 DEBUG("address: 0x%8.8x failed", address
);
789 int target_write_u32(struct target_s
*target
, u32 address
, u32 value
)
794 DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, value
);
796 target_buffer_set_u32(target
, value_buf
, value
);
797 if ((retval
= target
->type
->write_memory(target
, address
, 4, 1, value_buf
)) != ERROR_OK
)
799 DEBUG("failed: %i", retval
);
805 int target_write_u16(struct target_s
*target
, u32 address
, u16 value
)
810 DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, value
);
812 target_buffer_set_u16(target
, value_buf
, value
);
813 if ((retval
= target
->type
->write_memory(target
, address
, 2, 1, value_buf
)) != ERROR_OK
)
815 DEBUG("failed: %i", retval
);
821 int target_write_u8(struct target_s
*target
, u32 address
, u8 value
)
825 DEBUG("address: 0x%8.8x, value: 0x%2.2x", address
, value
);
827 if ((retval
= target
->type
->read_memory(target
, address
, 1, 1, &value
)) != ERROR_OK
)
829 DEBUG("failed: %i", retval
);
835 int target_register_user_commands(struct command_context_s
*cmd_ctx
)
837 register_command(cmd_ctx
, NULL
, "reg", handle_reg_command
, COMMAND_EXEC
, NULL
);
838 register_command(cmd_ctx
, NULL
, "poll", handle_poll_command
, COMMAND_EXEC
, "poll target state");
839 register_command(cmd_ctx
, NULL
, "wait_halt", handle_wait_halt_command
, COMMAND_EXEC
, "wait for target halt [time (s)]");
840 register_command(cmd_ctx
, NULL
, "halt", handle_halt_command
, COMMAND_EXEC
, "halt target");
841 register_command(cmd_ctx
, NULL
, "resume", handle_resume_command
, COMMAND_EXEC
, "resume target [addr]");
842 register_command(cmd_ctx
, NULL
, "step", handle_step_command
, COMMAND_EXEC
, "step one instruction");
843 register_command(cmd_ctx
, NULL
, "reset", handle_reset_command
, COMMAND_EXEC
, "reset target [run|halt|init|run_and_halt|run_and_init]");
844 register_command(cmd_ctx
, NULL
, "soft_reset_halt", handle_soft_reset_halt_command
, COMMAND_EXEC
, "halt the target and do a soft reset");
846 register_command(cmd_ctx
, NULL
, "mdw", handle_md_command
, COMMAND_EXEC
, "display memory words <addr> [count]");
847 register_command(cmd_ctx
, NULL
, "mdh", handle_md_command
, COMMAND_EXEC
, "display memory half-words <addr> [count]");
848 register_command(cmd_ctx
, NULL
, "mdb", handle_md_command
, COMMAND_EXEC
, "display memory bytes <addr> [count]");
850 register_command(cmd_ctx
, NULL
, "mww", handle_mw_command
, COMMAND_EXEC
, "write memory word <addr> <value>");
851 register_command(cmd_ctx
, NULL
, "mwh", handle_mw_command
, COMMAND_EXEC
, "write memory half-word <addr> <value>");
852 register_command(cmd_ctx
, NULL
, "mwb", handle_mw_command
, COMMAND_EXEC
, "write memory byte <addr> <value>");
854 register_command(cmd_ctx
, NULL
, "bp", handle_bp_command
, COMMAND_EXEC
, "set breakpoint <address> <length> [hw]");
855 register_command(cmd_ctx
, NULL
, "rbp", handle_rbp_command
, COMMAND_EXEC
, "remove breakpoint <adress>");
856 register_command(cmd_ctx
, NULL
, "wp", handle_wp_command
, COMMAND_EXEC
, "set watchpoint <address> <length> <r/w/a> [value] [mask]");
857 register_command(cmd_ctx
, NULL
, "rwp", handle_rwp_command
, COMMAND_EXEC
, "remove watchpoint <adress>");
859 register_command(cmd_ctx
, NULL
, "load_image", handle_load_image_command
, COMMAND_EXEC
, "load_image <file> <address> ['bin'|'ihex']");
860 register_command(cmd_ctx
, NULL
, "dump_image", handle_dump_image_command
, COMMAND_EXEC
, "dump_image <file> <address> <size>");
861 register_command(cmd_ctx
, NULL
, "load_binary", handle_load_image_command
, COMMAND_EXEC
, "[DEPRECATED] load_binary <file> <address>");
862 register_command(cmd_ctx
, NULL
, "dump_binary", handle_dump_image_command
, COMMAND_EXEC
, "[DEPRECATED] dump_binary <file> <address> <size>");
867 int handle_targets_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
869 target_t
*target
= targets
;
874 int num
= strtoul(args
[0], NULL
, 0);
879 target
= target
->next
;
883 cmd_ctx
->current_target
= num
;
885 command_print(cmd_ctx
, "%i is out of bounds, only %i targets are configured", num
, count
);
892 command_print(cmd_ctx
, "%i: %s (%s), state: %s", count
++, target
->type
->name
, target_endianess_strings
[target
->endianness
], target_state_strings
[target
->state
]);
893 target
= target
->next
;
899 int handle_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
906 ERROR("target command requires at least three arguments: <type> <endianess> <reset_mode>");
910 /* search for the specified target */
911 if (args
[0] && (args
[0][0] != 0))
913 for (i
= 0; target_types
[i
]; i
++)
915 if (strcmp(args
[0], target_types
[i
]->name
) == 0)
917 target_t
**last_target_p
= &targets
;
919 /* register target specific commands */
920 if (target_types
[i
]->register_commands(cmd_ctx
) != ERROR_OK
)
922 ERROR("couldn't register '%s' commands", args
[0]);
928 while ((*last_target_p
)->next
)
929 last_target_p
= &((*last_target_p
)->next
);
930 last_target_p
= &((*last_target_p
)->next
);
933 *last_target_p
= malloc(sizeof(target_t
));
935 (*last_target_p
)->type
= target_types
[i
];
937 if (strcmp(args
[1], "big") == 0)
938 (*last_target_p
)->endianness
= TARGET_BIG_ENDIAN
;
939 else if (strcmp(args
[1], "little") == 0)
940 (*last_target_p
)->endianness
= TARGET_LITTLE_ENDIAN
;
943 ERROR("endianness must be either 'little' or 'big', not '%s'", args
[1]);
947 /* what to do on a target reset */
948 if (strcmp(args
[2], "reset_halt") == 0)
949 (*last_target_p
)->reset_mode
= RESET_HALT
;
950 else if (strcmp(args
[2], "reset_run") == 0)
951 (*last_target_p
)->reset_mode
= RESET_RUN
;
952 else if (strcmp(args
[2], "reset_init") == 0)
953 (*last_target_p
)->reset_mode
= RESET_INIT
;
954 else if (strcmp(args
[2], "run_and_halt") == 0)
955 (*last_target_p
)->reset_mode
= RESET_RUN_AND_HALT
;
956 else if (strcmp(args
[2], "run_and_init") == 0)
957 (*last_target_p
)->reset_mode
= RESET_RUN_AND_INIT
;
960 ERROR("unknown target startup mode %s", args
[2]);
963 (*last_target_p
)->run_and_halt_time
= 1000; /* default 1s */
965 (*last_target_p
)->reset_script
= NULL
;
966 (*last_target_p
)->post_halt_script
= NULL
;
967 (*last_target_p
)->pre_resume_script
= NULL
;
969 (*last_target_p
)->working_area
= 0x0;
970 (*last_target_p
)->working_area_size
= 0x0;
971 (*last_target_p
)->working_areas
= NULL
;
972 (*last_target_p
)->backup_working_area
= 0;
974 (*last_target_p
)->state
= TARGET_UNKNOWN
;
975 (*last_target_p
)->reg_cache
= NULL
;
976 (*last_target_p
)->breakpoints
= NULL
;
977 (*last_target_p
)->watchpoints
= NULL
;
978 (*last_target_p
)->next
= NULL
;
979 (*last_target_p
)->arch_info
= NULL
;
981 (*last_target_p
)->type
->target_command(cmd_ctx
, cmd
, args
, argc
, *last_target_p
);
989 /* no matching target found */
992 ERROR("target '%s' not found", args
[0]);
999 /* usage: target_script <target#> <event> <script_file> */
1000 int handle_target_script_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1002 target_t
*target
= NULL
;
1006 ERROR("incomplete target_script command");
1010 target
= get_target_by_num(strtoul(args
[0], NULL
, 0));
1014 ERROR("target number '%s' not defined", args
[0]);
1018 if (strcmp(args
[1], "reset") == 0)
1020 if (target
->reset_script
)
1021 free(target
->reset_script
);
1022 target
->reset_script
= strdup(args
[2]);
1024 else if (strcmp(args
[1], "post_halt") == 0)
1026 if (target
->post_halt_script
)
1027 free(target
->post_halt_script
);
1028 target
->post_halt_script
= strdup(args
[2]);
1030 else if (strcmp(args
[1], "pre_resume") == 0)
1032 if (target
->pre_resume_script
)
1033 free(target
->pre_resume_script
);
1034 target
->pre_resume_script
= strdup(args
[2]);
1038 ERROR("unknown event type: '%s", args
[1]);
1045 int handle_run_and_halt_time_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1047 target_t
*target
= NULL
;
1051 ERROR("incomplete run_and_halt_time command");
1055 target
= get_target_by_num(strtoul(args
[0], NULL
, 0));
1059 ERROR("target number '%s' not defined", args
[0]);
1063 target
->run_and_halt_time
= strtoul(args
[1], NULL
, 0);
1068 int handle_working_area_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1070 target_t
*target
= NULL
;
1074 ERROR("incomplete working_area command. usage: working_area <target#> <address> <size> <'backup'|'nobackup'>");
1078 target
= get_target_by_num(strtoul(args
[0], NULL
, 0));
1082 ERROR("target number '%s' not defined", args
[0]);
1086 target
->working_area
= strtoul(args
[1], NULL
, 0);
1087 target
->working_area_size
= strtoul(args
[2], NULL
, 0);
1089 if (strcmp(args
[3], "backup") == 0)
1091 target
->backup_working_area
= 1;
1093 else if (strcmp(args
[3], "nobackup") == 0)
1095 target
->backup_working_area
= 0;
1099 ERROR("unrecognized <backup|nobackup> argument (%s)", args
[3]);
1107 /* process target state changes */
1108 int handle_target(void *priv
)
1111 target_t
*target
= targets
;
1115 /* only poll if target isn't already halted */
1116 if (target
->state
!= TARGET_HALTED
)
1118 if (target_continous_poll
)
1119 if ((retval
= target
->type
->poll(target
)) < 0)
1121 ERROR("couldn't poll target, exiting");
1126 target
= target
->next
;
1132 int handle_reg_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1141 target
= get_current_target(cmd_ctx
);
1143 /* list all available registers for the current target */
1146 reg_cache_t
*cache
= target
->reg_cache
;
1152 for (i
= 0; i
< cache
->num_regs
; i
++)
1154 value
= buf_to_str(cache
->reg_list
[i
].value
, cache
->reg_list
[i
].size
, 16);
1155 command_print(cmd_ctx
, "(%i) %s (/%i): 0x%s (dirty: %i, valid: %i)", count
++, cache
->reg_list
[i
].name
, cache
->reg_list
[i
].size
, value
, cache
->reg_list
[i
].dirty
, cache
->reg_list
[i
].valid
);
1158 cache
= cache
->next
;
1164 /* access a single register by its ordinal number */
1165 if ((args
[0][0] >= '0') && (args
[0][0] <= '9'))
1167 int num
= strtoul(args
[0], NULL
, 0);
1168 reg_cache_t
*cache
= target
->reg_cache
;
1174 for (i
= 0; i
< cache
->num_regs
; i
++)
1178 reg
= &cache
->reg_list
[i
];
1184 cache
= cache
->next
;
1189 command_print(cmd_ctx
, "%i is out of bounds, the current target has only %i registers (0 - %i)", num
, count
, count
- 1);
1192 } else /* access a single register by its name */
1194 reg
= register_get_by_name(target
->reg_cache
, args
[0], 1);
1198 command_print(cmd_ctx
, "register %s not found in current target", args
[0]);
1203 /* display a register */
1204 if ((argc
== 1) || ((argc
== 2) && !((args
[1][0] >= '0') && (args
[1][0] <= '9'))))
1206 if ((argc
== 2) && (strcmp(args
[1], "force") == 0))
1209 if (reg
->valid
== 0)
1211 reg_arch_type_t
*arch_type
= register_get_arch_type(reg
->arch_type
);
1212 if (arch_type
== NULL
)
1214 ERROR("BUG: encountered unregistered arch type");
1217 arch_type
->get(reg
);
1219 value
= buf_to_str(reg
->value
, reg
->size
, 16);
1220 command_print(cmd_ctx
, "%s (/%i): 0x%s", reg
->name
, reg
->size
, value
);
1225 /* set register value */
1228 u8
*buf
= malloc(CEIL(reg
->size
, 8));
1229 str_to_buf(args
[1], strlen(args
[1]), buf
, reg
->size
, 0);
1231 reg_arch_type_t
*arch_type
= register_get_arch_type(reg
->arch_type
);
1232 if (arch_type
== NULL
)
1234 ERROR("BUG: encountered unregistered arch type");
1238 arch_type
->set(reg
, buf
);
1240 value
= buf_to_str(reg
->value
, reg
->size
, 16);
1241 command_print(cmd_ctx
, "%s (/%i): 0x%s", reg
->name
, reg
->size
, value
);
1249 command_print(cmd_ctx
, "usage: reg <#|name> [value]");
1254 int handle_poll_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1256 target_t
*target
= get_current_target(cmd_ctx
);
1261 command_print(cmd_ctx
, "target state: %s", target_state_strings
[target
->type
->poll(target
)]);
1262 if (target
->state
== TARGET_HALTED
)
1264 target
->type
->arch_state(target
, buffer
, 512);
1266 command_print(cmd_ctx
, "%s", buffer
);
1271 if (strcmp(args
[0], "on") == 0)
1273 target_continous_poll
= 1;
1275 else if (strcmp(args
[0], "off") == 0)
1277 target_continous_poll
= 0;
1285 int handle_wait_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1287 target_t
*target
= get_current_target(cmd_ctx
);
1288 struct timeval timeout
, now
;
1290 gettimeofday(&timeout
, NULL
);
1292 timeval_add_time(&timeout
, 5, 0);
1296 timeval_add_time(&timeout
, strtoul(args
[0], &end
, 0), 0);
1298 command_print(cmd_ctx
, "usage: wait_halt [seconds]");
1303 command_print(cmd_ctx
, "waiting for target halted...");
1305 while(target
->type
->poll(target
))
1307 if (target
->state
== TARGET_HALTED
)
1309 command_print(cmd_ctx
, "target halted");
1312 target_call_timer_callbacks();
1314 gettimeofday(&now
, NULL
);
1315 if ((now
.tv_sec
>= timeout
.tv_sec
) && (now
.tv_usec
>= timeout
.tv_usec
))
1317 command_print(cmd_ctx
, "timed out while waiting for target halt");
1318 ERROR("timed out while waiting for target halt");
1326 int handle_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1329 target_t
*target
= get_current_target(cmd_ctx
);
1333 command_print(cmd_ctx
, "requesting target halt...");
1335 if ((retval
= target
->type
->halt(target
)) != ERROR_OK
)
1339 case ERROR_TARGET_ALREADY_HALTED
:
1340 command_print(cmd_ctx
, "target already halted");
1342 case ERROR_TARGET_TIMEOUT
:
1343 command_print(cmd_ctx
, "target timed out... shutting down");
1346 command_print(cmd_ctx
, "unknown error... shutting down");
1355 /* what to do on daemon startup */
1356 int handle_daemon_startup_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1360 if (strcmp(args
[0], "attach") == 0)
1362 startup_mode
= DAEMON_ATTACH
;
1365 else if (strcmp(args
[0], "reset") == 0)
1367 startup_mode
= DAEMON_RESET
;
1372 WARNING("invalid daemon_startup configuration directive: %s", args
[0]);
1377 int handle_soft_reset_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1379 target_t
*target
= get_current_target(cmd_ctx
);
1382 command_print(cmd_ctx
, "requesting target halt and executing a soft reset");
1384 if ((retval
= target
->type
->soft_reset_halt(target
)) != ERROR_OK
)
1388 case ERROR_TARGET_TIMEOUT
:
1389 command_print(cmd_ctx
, "target timed out... shutting down");
1392 command_print(cmd_ctx
, "unknown error... shutting down");
1400 int handle_reset_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1402 target_t
*target
= get_current_target(cmd_ctx
);
1403 enum target_reset_mode reset_mode
= RESET_RUN
;
1409 if (strcmp("run", args
[0]) == 0)
1410 reset_mode
= RESET_RUN
;
1411 else if (strcmp("halt", args
[0]) == 0)
1412 reset_mode
= RESET_HALT
;
1413 else if (strcmp("init", args
[0]) == 0)
1414 reset_mode
= RESET_INIT
;
1415 else if (strcmp("run_and_halt", args
[0]) == 0)
1417 reset_mode
= RESET_RUN_AND_HALT
;
1420 target
->run_and_halt_time
= strtoul(args
[1], NULL
, 0);
1423 else if (strcmp("run_and_init", args
[0]) == 0)
1425 reset_mode
= RESET_RUN_AND_INIT
;
1428 target
->run_and_halt_time
= strtoul(args
[1], NULL
, 0);
1433 command_print(cmd_ctx
, "usage: reset ['run', 'halt', 'init', 'run_and_halt', 'run_and_init]");
1436 target
->reset_mode
= reset_mode
;
1439 target_process_reset(cmd_ctx
);
1444 int handle_resume_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1447 target_t
*target
= get_current_target(cmd_ctx
);
1452 retval
= target
->type
->resume(target
, 1, 0, 1, 0); /* current pc, addr = 0, handle breakpoints, not debugging */
1454 retval
= target
->type
->resume(target
, 0, strtoul(args
[0], NULL
, 0), 1, 0); /* addr = args[0], handle breakpoints, not debugging */
1457 command_print(cmd_ctx
, "usage: resume [address]");
1461 if (retval
!= ERROR_OK
)
1465 case ERROR_TARGET_NOT_HALTED
:
1466 command_print(cmd_ctx
, "target not halted");
1469 command_print(cmd_ctx
, "unknown error... shutting down");
1477 int handle_step_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1479 target_t
*target
= get_current_target(cmd_ctx
);
1484 target
->type
->step(target
, 1, 0, 1); /* current pc, addr = 0, handle breakpoints */
1487 target
->type
->step(target
, 0, strtoul(args
[0], NULL
, 0), 1); /* addr = args[0], handle breakpoints */
1492 int handle_md_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1505 target_t
*target
= get_current_target(cmd_ctx
);
1511 count
= strtoul(args
[1], NULL
, 0);
1513 address
= strtoul(args
[0], NULL
, 0);
1531 buffer
= calloc(count
, size
);
1532 if ((retval
= target
->type
->read_memory(target
, address
, size
, count
, buffer
)) != ERROR_OK
)
1536 case ERROR_TARGET_UNALIGNED_ACCESS
:
1537 command_print(cmd_ctx
, "error: address not aligned");
1539 case ERROR_TARGET_NOT_HALTED
:
1540 command_print(cmd_ctx
, "error: target must be halted for memory accesses");
1542 case ERROR_TARGET_DATA_ABORT
:
1543 command_print(cmd_ctx
, "error: access caused data abort, system possibly corrupted");
1546 command_print(cmd_ctx
, "error: unknown error");
1554 for (i
= 0; i
< count
; i
++)
1557 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "0x%8.8x: ", address
+ (i
*size
));
1562 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%8.8x ", target_buffer_get_u32(target
, &buffer
[i
*4]));
1565 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%4.4x ", target_buffer_get_u16(target
, &buffer
[i
*2]));
1568 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%2.2x ", buffer
[i
*1]);
1572 if ((i
%8 == 7) || (i
== count
- 1))
1574 command_print(cmd_ctx
, output
);
1584 int handle_mw_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1589 target_t
*target
= get_current_target(cmd_ctx
);
1595 address
= strtoul(args
[0], NULL
, 0);
1596 value
= strtoul(args
[1], NULL
, 0);
1601 target_buffer_set_u32(target
, value_buf
, value
);
1602 retval
= target
->type
->write_memory(target
, address
, 4, 1, value_buf
);
1605 target_buffer_set_u16(target
, value_buf
, value
);
1606 retval
= target
->type
->write_memory(target
, address
, 2, 1, value_buf
);
1609 value_buf
[0] = value
;
1610 retval
= target
->type
->write_memory(target
, address
, 1, 1, value_buf
);
1618 case ERROR_TARGET_UNALIGNED_ACCESS
:
1619 command_print(cmd_ctx
, "error: address not aligned");
1621 case ERROR_TARGET_DATA_ABORT
:
1622 command_print(cmd_ctx
, "error: access caused data abort, system possibly corrupted");
1624 case ERROR_TARGET_NOT_HALTED
:
1625 command_print(cmd_ctx
, "error: target must be halted for memory accesses");
1630 command_print(cmd_ctx
, "error: unknown error");
1638 int handle_load_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1646 enum fileio_pri_type pri_type
= FILEIO_IMAGE
;
1647 fileio_image_t image_info
;
1648 enum fileio_sec_type sec_type
;
1650 duration_t duration
;
1651 char *duration_text
;
1653 target_t
*target
= get_current_target(cmd_ctx
);
1657 command_print(cmd_ctx
, "usage: load_image <filename> <address> [type]");
1661 memset(&file
, 0, sizeof(fileio_t
));
1662 fileio_identify_image_type(&sec_type
, (argc
== 3) ? args
[2] : NULL
);
1664 image_info
.base_address
= strtoul(args
[1], NULL
, 0);
1665 image_info
.has_start_address
= 0;
1667 buffer
= malloc(128 * 1024);
1669 duration_start_measure(&duration
);
1671 if (fileio_open(&file
, args
[0], FILEIO_READ
,
1672 pri_type
, &image_info
, sec_type
) != ERROR_OK
)
1674 command_print(cmd_ctx
, "load_image error: %s", file
.error_str
);
1678 binary_size
= file
.size
;
1679 address
= image_info
.base_address
;
1680 while ((binary_size
> 0) &&
1681 (fileio_read(&file
, 128 * 1024, buffer
, &buf_cnt
) == ERROR_OK
))
1683 target_write_buffer(target
, address
, buf_cnt
, buffer
);
1685 binary_size
-= buf_cnt
;
1690 duration_stop_measure(&duration
, &duration_text
);
1691 command_print(cmd_ctx
, "downloaded %lli byte in %s", file
.size
, duration_text
);
1692 free(duration_text
);
1694 fileio_close(&file
);
1700 int handle_dump_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1703 fileio_image_t image_info
;
1709 duration_t duration
;
1710 char *duration_text
;
1712 target_t
*target
= get_current_target(cmd_ctx
);
1716 command_print(cmd_ctx
, "usage: dump_image <filename> <address> <size>");
1720 address
= strtoul(args
[1], NULL
, 0);
1721 size
= strtoul(args
[2], NULL
, 0);
1723 if ((address
& 3) || (size
& 3))
1725 command_print(cmd_ctx
, "only 32-bit aligned address and size are supported");
1729 image_info
.base_address
= address
;
1730 image_info
.has_start_address
= 0;
1732 if (fileio_open(&file
, args
[0], FILEIO_WRITE
,
1733 FILEIO_IMAGE
, &image_info
, FILEIO_PLAIN
) != ERROR_OK
)
1735 command_print(cmd_ctx
, "dump_image error: %s", file
.error_str
);
1739 duration_start_measure(&duration
);
1744 u32 this_run_size
= (size
> 560) ? 560 : size
;
1746 target
->type
->read_memory(target
, address
, 4, this_run_size
/ 4, buffer
);
1747 fileio_write(&file
, this_run_size
, buffer
, &size_written
);
1749 size
-= this_run_size
;
1750 address
+= this_run_size
;
1753 fileio_close(&file
);
1755 duration_stop_measure(&duration
, &duration_text
);
1756 command_print(cmd_ctx
, "dumped %lli byte in %s", file
.size
, duration_text
);
1757 free(duration_text
);
1763 int handle_bp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1766 target_t
*target
= get_current_target(cmd_ctx
);
1770 breakpoint_t
*breakpoint
= target
->breakpoints
;
1774 if (breakpoint
->type
== BKPT_SOFT
)
1776 char* buf
= buf_to_str(breakpoint
->orig_instr
, breakpoint
->length
, 16);
1777 command_print(cmd_ctx
, "0x%8.8x, 0x%x, %i, 0x%s", breakpoint
->address
, breakpoint
->length
, breakpoint
->set
, buf
);
1782 command_print(cmd_ctx
, "0x%8.8x, 0x%x, %i", breakpoint
->address
, breakpoint
->length
, breakpoint
->set
);
1784 breakpoint
= breakpoint
->next
;
1792 length
= strtoul(args
[1], NULL
, 0);
1795 if (strcmp(args
[2], "hw") == 0)
1798 if ((retval
= breakpoint_add(target
, strtoul(args
[0], NULL
, 0), length
, hw
)) != ERROR_OK
)
1802 case ERROR_TARGET_NOT_HALTED
:
1803 command_print(cmd_ctx
, "target must be halted to set breakpoints");
1805 case ERROR_TARGET_RESOURCE_NOT_AVAILABLE
:
1806 command_print(cmd_ctx
, "no more breakpoints available");
1809 command_print(cmd_ctx
, "unknown error, breakpoint not set");
1815 command_print(cmd_ctx
, "breakpoint added at address 0x%8.8x", strtoul(args
[0], NULL
, 0));
1820 command_print(cmd_ctx
, "usage: bp <address> <length> ['hw']");
1826 int handle_rbp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1828 target_t
*target
= get_current_target(cmd_ctx
);
1831 breakpoint_remove(target
, strtoul(args
[0], NULL
, 0));
1836 int handle_wp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1838 target_t
*target
= get_current_target(cmd_ctx
);
1842 watchpoint_t
*watchpoint
= target
->watchpoints
;
1846 command_print(cmd_ctx
, "address: 0x%8.8x, mask: 0x%8.8x, r/w/a: %i, value: 0x%8.8x, mask: 0x%8.8x", watchpoint
->address
, watchpoint
->length
, watchpoint
->rw
, watchpoint
->value
, watchpoint
->mask
);
1847 watchpoint
= watchpoint
->next
;
1852 enum watchpoint_rw type
= WPT_ACCESS
;
1853 u32 data_value
= 0x0;
1854 u32 data_mask
= 0xffffffff;
1870 command_print(cmd_ctx
, "usage: wp <address> <length> [r/w/a] [value] [mask]");
1876 data_value
= strtoul(args
[3], NULL
, 0);
1880 data_mask
= strtoul(args
[4], NULL
, 0);
1882 watchpoint_add(target
, strtoul(args
[0], NULL
, 0), strtoul(args
[1], NULL
, 0), type
, data_value
, data_mask
);
1886 command_print(cmd_ctx
, "usage: wp <address> <length> [r/w/a] [value] [mask]");
1892 int handle_rwp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1894 target_t
*target
= get_current_target(cmd_ctx
);
1897 watchpoint_remove(target
, strtoul(args
[0], NULL
, 0));
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)