1 /***************************************************************************
2 * Copyright (C) 2005 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * Copyright (C) 2007,2008 Øyvind Harboe *
6 * oyvind.harboe@zylin.com *
8 * Copyright (C) 2008, Duane Ellis *
9 * openocd@duaneeellis.com *
11 * Copyright (C) 2008 by Spencer Oliver *
12 * spen@spen-soft.co.uk *
14 * Copyright (C) 2008 by Rick Altherr *
15 * kc8apf@kc8apf.net> *
17 * This program is free software; you can redistribute it and/or modify *
18 * it under the terms of the GNU General Public License as published by *
19 * the Free Software Foundation; either version 2 of the License, or *
20 * (at your option) any later version. *
22 * This program is distributed in the hope that it will be useful, *
23 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
24 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
25 * GNU General Public License for more details. *
27 * You should have received a copy of the GNU General Public License *
28 * along with this program; if not, write to the *
29 * Free Software Foundation, Inc., *
30 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
31 ***************************************************************************/
36 #include "replacements.h"
38 #include "target_request.h"
41 #include "configuration.h"
42 #include "binarybuffer.h"
49 #include <sys/types.h>
57 #include <time_support.h>
62 int cli_target_callback_event_handler(struct target_s
*target
, enum target_event event
, void *priv
);
65 int handle_targets_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
67 int handle_reg_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
68 int handle_poll_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
69 int handle_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
70 int handle_wait_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
71 int handle_reset_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
72 int handle_soft_reset_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
73 int handle_resume_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
74 int handle_step_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
75 int handle_md_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
76 int handle_mw_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
77 int handle_load_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
78 int handle_dump_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
79 int handle_verify_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
80 int handle_bp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
81 int handle_rbp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
82 int handle_wp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
83 int handle_rwp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
84 int handle_virt2phys_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
);
85 int handle_profile_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
86 static int jim_array2mem(Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
);
87 static int jim_mem2array(Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
);
88 static int jim_target( Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
);
90 static int target_array2mem(Jim_Interp
*interp
, target_t
*target
, int argc
, Jim_Obj
*const *argv
);
91 static int target_mem2array(Jim_Interp
*interp
, target_t
*target
, int argc
, Jim_Obj
*const *argv
);
96 extern target_type_t arm7tdmi_target
;
97 extern target_type_t arm720t_target
;
98 extern target_type_t arm9tdmi_target
;
99 extern target_type_t arm920t_target
;
100 extern target_type_t arm966e_target
;
101 extern target_type_t arm926ejs_target
;
102 extern target_type_t feroceon_target
;
103 extern target_type_t xscale_target
;
104 extern target_type_t cortexm3_target
;
105 extern target_type_t arm11_target
;
106 extern target_type_t mips_m4k_target
;
108 target_type_t
*target_types
[] =
124 target_t
*all_targets
= NULL
;
125 target_event_callback_t
*target_event_callbacks
= NULL
;
126 target_timer_callback_t
*target_timer_callbacks
= NULL
;
128 const Jim_Nvp nvp_assert
[] = {
129 { .name
= "assert", NVP_ASSERT
},
130 { .name
= "deassert", NVP_DEASSERT
},
131 { .name
= "T", NVP_ASSERT
},
132 { .name
= "F", NVP_DEASSERT
},
133 { .name
= "t", NVP_ASSERT
},
134 { .name
= "f", NVP_DEASSERT
},
135 { .name
= NULL
, .value
= -1 }
138 const Jim_Nvp nvp_error_target
[] = {
139 { .value
= ERROR_TARGET_INVALID
, .name
= "err-invalid" },
140 { .value
= ERROR_TARGET_INIT_FAILED
, .name
= "err-init-failed" },
141 { .value
= ERROR_TARGET_TIMEOUT
, .name
= "err-timeout" },
142 { .value
= ERROR_TARGET_NOT_HALTED
, .name
= "err-not-halted" },
143 { .value
= ERROR_TARGET_FAILURE
, .name
= "err-failure" },
144 { .value
= ERROR_TARGET_UNALIGNED_ACCESS
, .name
= "err-unaligned-access" },
145 { .value
= ERROR_TARGET_DATA_ABORT
, .name
= "err-data-abort" },
146 { .value
= ERROR_TARGET_RESOURCE_NOT_AVAILABLE
, .name
= "err-resource-not-available" },
147 { .value
= ERROR_TARGET_TRANSLATION_FAULT
, .name
= "err-translation-fault" },
148 { .value
= ERROR_TARGET_NOT_RUNNING
, .name
= "err-not-running" },
149 { .value
= ERROR_TARGET_NOT_EXAMINED
, .name
= "err-not-examined" },
150 { .value
= -1, .name
= NULL
}
153 const char *target_strerror_safe( int err
)
157 n
= Jim_Nvp_value2name_simple( nvp_error_target
, err
);
158 if( n
->name
== NULL
){
165 const Jim_Nvp nvp_target_event
[] = {
166 { .value
= TARGET_EVENT_OLD_gdb_program_config
, .name
= "old-gdb_program_config" },
167 { .value
= TARGET_EVENT_OLD_pre_resume
, .name
= "old-pre_resume" },
170 { .value
= TARGET_EVENT_EARLY_HALTED
, .name
= "early-halted" },
171 { .value
= TARGET_EVENT_HALTED
, .name
= "halted" },
172 { .value
= TARGET_EVENT_RESUMED
, .name
= "resumed" },
173 { .value
= TARGET_EVENT_RESUME_START
, .name
= "resume-start" },
174 { .value
= TARGET_EVENT_RESUME_END
, .name
= "resume-end" },
177 { .name
= "gdb-start", .value
= TARGET_EVENT_GDB_START
},
178 { .name
= "gdb-end", .value
= TARGET_EVENT_GDB_END
},
181 /* historical name */
183 { .value
= TARGET_EVENT_RESET_START
, .name
= "reset-start" },
185 { .value
= TARGET_EVENT_RESET_ASSERT_PRE
, .name
= "reset-assert-pre" },
186 { .value
= TARGET_EVENT_RESET_ASSERT_POST
, .name
= "reset-assert-post" },
187 { .value
= TARGET_EVENT_RESET_DEASSERT_PRE
, .name
= "reset-deassert-pre" },
188 { .value
= TARGET_EVENT_RESET_DEASSERT_POST
, .name
= "reset-deassert-post" },
189 { .value
= TARGET_EVENT_RESET_HALT_PRE
, .name
= "reset-halt-pre" },
190 { .value
= TARGET_EVENT_RESET_HALT_POST
, .name
= "reset-halt-post" },
191 { .value
= TARGET_EVENT_RESET_WAIT_PRE
, .name
= "reset-wait-pre" },
192 { .value
= TARGET_EVENT_RESET_WAIT_POST
, .name
= "reset-wait-post" },
193 { .value
= TARGET_EVENT_RESET_INIT
, .name
= "reset-init" },
194 { .value
= TARGET_EVENT_RESET_END
, .name
= "reset-end" },
200 { .value
= TARGET_EVENT_EXAMINE_START
, .name
= "examine-start" },
201 { .value
= TARGET_EVENT_EXAMINE_END
, .name
= "examine-end" },
204 { .value
= TARGET_EVENT_DEBUG_HALTED
, .name
= "debug-halted" },
205 { .value
= TARGET_EVENT_DEBUG_RESUMED
, .name
= "debug-resumed" },
207 { .value
= TARGET_EVENT_GDB_ATTACH
, .name
= "gdb-attach" },
208 { .value
= TARGET_EVENT_GDB_DETACH
, .name
= "gdb-detach" },
211 { .value
= TARGET_EVENT_GDB_FLASH_WRITE_START
, .name
= "gdb-flash-write-start" },
212 { .value
= TARGET_EVENT_GDB_FLASH_WRITE_END
, .name
= "gdb-flash-write-end" },
214 { .value
= TARGET_EVENT_GDB_FLASH_ERASE_START
, .name
= "gdb-flash-erase-start" },
215 { .value
= TARGET_EVENT_GDB_FLASH_ERASE_END
, .name
= "gdb-flash-erase-end" },
217 { .value
= TARGET_EVENT_RESUME_START
, .name
= "resume-start" },
218 { .value
= TARGET_EVENT_RESUMED
, .name
= "resume-ok" },
219 { .value
= TARGET_EVENT_RESUME_END
, .name
= "resume-end" },
221 { .name
= NULL
, .value
= -1 }
224 const Jim_Nvp nvp_target_state
[] = {
225 { .name
= "unknown", .value
= TARGET_UNKNOWN
},
226 { .name
= "running", .value
= TARGET_RUNNING
},
227 { .name
= "halted", .value
= TARGET_HALTED
},
228 { .name
= "reset", .value
= TARGET_RESET
},
229 { .name
= "debug-running", .value
= TARGET_DEBUG_RUNNING
},
230 { .name
= NULL
, .value
= -1 },
234 const Jim_Nvp nvp_target_debug_reason
[] = {
235 { .name
= "debug-request" , .value
= DBG_REASON_DBGRQ
},
236 { .name
= "breakpoint" , .value
= DBG_REASON_BREAKPOINT
},
237 { .name
= "watchpoint" , .value
= DBG_REASON_WATCHPOINT
},
238 { .name
= "watchpoint-and-breakpoint", .value
= DBG_REASON_WPTANDBKPT
},
239 { .name
= "single-step" , .value
= DBG_REASON_SINGLESTEP
},
240 { .name
= "target-not-halted" , .value
= DBG_REASON_NOTHALTED
},
241 { .name
= "undefined" , .value
= DBG_REASON_UNDEFINED
},
242 { .name
= NULL
, .value
= -1 },
246 const Jim_Nvp nvp_target_endian
[] = {
247 { .name
= "big", .value
= TARGET_BIG_ENDIAN
},
248 { .name
= "little", .value
= TARGET_LITTLE_ENDIAN
},
249 { .name
= "be", .value
= TARGET_BIG_ENDIAN
},
250 { .name
= "le", .value
= TARGET_LITTLE_ENDIAN
},
251 { .name
= NULL
, .value
= -1 },
254 const Jim_Nvp nvp_reset_modes
[] = {
255 { .name
= "unknown", .value
= RESET_UNKNOWN
},
256 { .name
= "run" , .value
= RESET_RUN
},
257 { .name
= "halt" , .value
= RESET_HALT
},
258 { .name
= "init" , .value
= RESET_INIT
},
259 { .name
= NULL
, .value
= -1 },
263 max_target_number( void )
271 if( x
< t
->target_number
){
272 x
= (t
->target_number
)+1;
279 /* determine the number of the new target */
281 new_target_number( void )
286 /* number is 0 based */
290 if( x
< t
->target_number
){
291 x
= t
->target_number
;
298 static int target_continous_poll
= 1;
300 /* read a u32 from a buffer in target memory endianness */
301 u32
target_buffer_get_u32(target_t
*target
, u8
*buffer
)
303 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
304 return le_to_h_u32(buffer
);
306 return be_to_h_u32(buffer
);
309 /* read a u16 from a buffer in target memory endianness */
310 u16
target_buffer_get_u16(target_t
*target
, u8
*buffer
)
312 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
313 return le_to_h_u16(buffer
);
315 return be_to_h_u16(buffer
);
318 /* read a u8 from a buffer in target memory endianness */
319 u8
target_buffer_get_u8(target_t
*target
, u8
*buffer
)
321 return *buffer
& 0x0ff;
324 /* write a u32 to a buffer in target memory endianness */
325 void target_buffer_set_u32(target_t
*target
, u8
*buffer
, u32 value
)
327 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
328 h_u32_to_le(buffer
, value
);
330 h_u32_to_be(buffer
, value
);
333 /* write a u16 to a buffer in target memory endianness */
334 void target_buffer_set_u16(target_t
*target
, u8
*buffer
, u16 value
)
336 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
337 h_u16_to_le(buffer
, value
);
339 h_u16_to_be(buffer
, value
);
342 /* write a u8 to a buffer in target memory endianness */
343 void target_buffer_set_u8(target_t
*target
, u8
*buffer
, u8 value
)
348 /* returns a pointer to the n-th configured target */
349 target_t
* get_target_by_num(int num
)
351 target_t
*target
= all_targets
;
354 if( target
->target_number
== num
){
357 target
= target
->next
;
363 int get_num_by_target(target_t
*query_target
)
365 return query_target
->target_number
;
368 target_t
* get_current_target(command_context_t
*cmd_ctx
)
370 target_t
*target
= get_target_by_num(cmd_ctx
->current_target
);
374 LOG_ERROR("BUG: current_target out of bounds");
382 int target_poll(struct target_s
*target
)
384 /* We can't poll until after examine */
385 if (!target
->type
->examined
)
387 /* Fail silently lest we pollute the log */
390 return target
->type
->poll(target
);
393 int target_halt(struct target_s
*target
)
395 /* We can't poll until after examine */
396 if (!target
->type
->examined
)
398 LOG_ERROR("Target not examined yet");
401 return target
->type
->halt(target
);
404 int target_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
)
408 /* We can't poll until after examine */
409 if (!target
->type
->examined
)
411 LOG_ERROR("Target not examined yet");
415 /* note that resume *must* be asynchronous. The CPU can halt before we poll. The CPU can
416 * even halt at the current PC as a result of a software breakpoint being inserted by (a bug?)
419 if ((retval
= target
->type
->resume(target
, current
, address
, handle_breakpoints
, debug_execution
)) != ERROR_OK
)
426 int target_process_reset(struct command_context_s
*cmd_ctx
, enum target_reset_mode reset_mode
)
431 n
= Jim_Nvp_value2name_simple( nvp_reset_modes
, reset_mode
);
432 if( n
->name
== NULL
){
433 LOG_ERROR("invalid reset mode");
437 sprintf( buf
, "ocd_process_reset %s", n
->name
);
438 retval
= Jim_Eval( interp
, buf
);
440 if(retval
!= JIM_OK
) {
441 Jim_PrintErrorMessage(interp
);
445 /* We want any events to be processed before the prompt */
446 retval
= target_call_timer_callbacks_now();
452 static int default_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
)
458 static int default_mmu(struct target_s
*target
, int *enabled
)
464 static int default_examine(struct target_s
*target
)
466 target
->type
->examined
= 1;
471 /* Targets that correctly implement init+examine, i.e.
472 * no communication with target during init:
476 int target_examine(void)
478 int retval
= ERROR_OK
;
479 target_t
*target
= all_targets
;
482 if ((retval
= target
->type
->examine(target
))!=ERROR_OK
)
484 target
= target
->next
;
489 static int target_write_memory_imp(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
491 if (!target
->type
->examined
)
493 LOG_ERROR("Target not examined yet");
496 return target
->type
->write_memory_imp(target
, address
, size
, count
, buffer
);
499 static int target_read_memory_imp(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
501 if (!target
->type
->examined
)
503 LOG_ERROR("Target not examined yet");
506 return target
->type
->read_memory_imp(target
, address
, size
, count
, buffer
);
509 static int target_soft_reset_halt_imp(struct target_s
*target
)
511 if (!target
->type
->examined
)
513 LOG_ERROR("Target not examined yet");
516 return target
->type
->soft_reset_halt_imp(target
);
519 static int target_run_algorithm_imp(struct target_s
*target
, int num_mem_params
, mem_param_t
*mem_params
, int num_reg_params
, reg_param_t
*reg_param
, u32 entry_point
, u32 exit_point
, int timeout_ms
, void *arch_info
)
521 if (!target
->type
->examined
)
523 LOG_ERROR("Target not examined yet");
526 return target
->type
->run_algorithm_imp(target
, num_mem_params
, mem_params
, num_reg_params
, reg_param
, entry_point
, exit_point
, timeout_ms
, arch_info
);
529 int target_init(struct command_context_s
*cmd_ctx
)
531 target_t
*target
= all_targets
;
536 target
->type
->examined
= 0;
537 if (target
->type
->examine
== NULL
)
539 target
->type
->examine
= default_examine
;
542 if ((retval
= target
->type
->init_target(cmd_ctx
, target
)) != ERROR_OK
)
544 LOG_ERROR("target '%s' init failed", target
->type
->name
);
548 /* Set up default functions if none are provided by target */
549 if (target
->type
->virt2phys
== NULL
)
551 target
->type
->virt2phys
= default_virt2phys
;
553 target
->type
->virt2phys
= default_virt2phys
;
554 /* a non-invasive way(in terms of patches) to add some code that
555 * runs before the type->write/read_memory implementation
557 target
->type
->write_memory_imp
= target
->type
->write_memory
;
558 target
->type
->write_memory
= target_write_memory_imp
;
559 target
->type
->read_memory_imp
= target
->type
->read_memory
;
560 target
->type
->read_memory
= target_read_memory_imp
;
561 target
->type
->soft_reset_halt_imp
= target
->type
->soft_reset_halt
;
562 target
->type
->soft_reset_halt
= target_soft_reset_halt_imp
;
563 target
->type
->run_algorithm_imp
= target
->type
->run_algorithm
;
564 target
->type
->run_algorithm
= target_run_algorithm_imp
;
567 if (target
->type
->mmu
== NULL
)
569 target
->type
->mmu
= default_mmu
;
571 target
= target
->next
;
576 if((retval
= target_register_user_commands(cmd_ctx
)) != ERROR_OK
)
578 if((retval
= target_register_timer_callback(handle_target
, 100, 1, NULL
)) != ERROR_OK
)
585 int target_register_event_callback(int (*callback
)(struct target_s
*target
, enum target_event event
, void *priv
), void *priv
)
587 target_event_callback_t
**callbacks_p
= &target_event_callbacks
;
589 if (callback
== NULL
)
591 return ERROR_INVALID_ARGUMENTS
;
596 while ((*callbacks_p
)->next
)
597 callbacks_p
= &((*callbacks_p
)->next
);
598 callbacks_p
= &((*callbacks_p
)->next
);
601 (*callbacks_p
) = malloc(sizeof(target_event_callback_t
));
602 (*callbacks_p
)->callback
= callback
;
603 (*callbacks_p
)->priv
= priv
;
604 (*callbacks_p
)->next
= NULL
;
609 int target_register_timer_callback(int (*callback
)(void *priv
), int time_ms
, int periodic
, void *priv
)
611 target_timer_callback_t
**callbacks_p
= &target_timer_callbacks
;
614 if (callback
== NULL
)
616 return ERROR_INVALID_ARGUMENTS
;
621 while ((*callbacks_p
)->next
)
622 callbacks_p
= &((*callbacks_p
)->next
);
623 callbacks_p
= &((*callbacks_p
)->next
);
626 (*callbacks_p
) = malloc(sizeof(target_timer_callback_t
));
627 (*callbacks_p
)->callback
= callback
;
628 (*callbacks_p
)->periodic
= periodic
;
629 (*callbacks_p
)->time_ms
= time_ms
;
631 gettimeofday(&now
, NULL
);
632 (*callbacks_p
)->when
.tv_usec
= now
.tv_usec
+ (time_ms
% 1000) * 1000;
633 time_ms
-= (time_ms
% 1000);
634 (*callbacks_p
)->when
.tv_sec
= now
.tv_sec
+ (time_ms
/ 1000);
635 if ((*callbacks_p
)->when
.tv_usec
> 1000000)
637 (*callbacks_p
)->when
.tv_usec
= (*callbacks_p
)->when
.tv_usec
- 1000000;
638 (*callbacks_p
)->when
.tv_sec
+= 1;
641 (*callbacks_p
)->priv
= priv
;
642 (*callbacks_p
)->next
= NULL
;
647 int target_unregister_event_callback(int (*callback
)(struct target_s
*target
, enum target_event event
, void *priv
), void *priv
)
649 target_event_callback_t
**p
= &target_event_callbacks
;
650 target_event_callback_t
*c
= target_event_callbacks
;
652 if (callback
== NULL
)
654 return ERROR_INVALID_ARGUMENTS
;
659 target_event_callback_t
*next
= c
->next
;
660 if ((c
->callback
== callback
) && (c
->priv
== priv
))
674 int target_unregister_timer_callback(int (*callback
)(void *priv
), void *priv
)
676 target_timer_callback_t
**p
= &target_timer_callbacks
;
677 target_timer_callback_t
*c
= target_timer_callbacks
;
679 if (callback
== NULL
)
681 return ERROR_INVALID_ARGUMENTS
;
686 target_timer_callback_t
*next
= c
->next
;
687 if ((c
->callback
== callback
) && (c
->priv
== priv
))
701 int target_call_event_callbacks(target_t
*target
, enum target_event event
)
703 target_event_callback_t
*callback
= target_event_callbacks
;
704 target_event_callback_t
*next_callback
;
706 if (event
== TARGET_EVENT_HALTED
)
708 /* execute early halted first */
709 target_call_event_callbacks(target
, TARGET_EVENT_EARLY_HALTED
);
713 LOG_DEBUG("target event %i (%s)",
715 Jim_Nvp_value2name_simple( nvp_target_event
, event
)->name
);
717 target_handle_event( target
, event
);
721 next_callback
= callback
->next
;
722 callback
->callback(target
, event
, callback
->priv
);
723 callback
= next_callback
;
729 static int target_call_timer_callbacks_check_time(int checktime
)
731 target_timer_callback_t
*callback
= target_timer_callbacks
;
732 target_timer_callback_t
*next_callback
;
737 gettimeofday(&now
, NULL
);
741 next_callback
= callback
->next
;
743 if ((!checktime
&&callback
->periodic
)||
744 (((now
.tv_sec
>= callback
->when
.tv_sec
) && (now
.tv_usec
>= callback
->when
.tv_usec
))
745 || (now
.tv_sec
> callback
->when
.tv_sec
)))
747 if(callback
->callback
!= NULL
)
749 callback
->callback(callback
->priv
);
750 if (callback
->periodic
)
752 int time_ms
= callback
->time_ms
;
753 callback
->when
.tv_usec
= now
.tv_usec
+ (time_ms
% 1000) * 1000;
754 time_ms
-= (time_ms
% 1000);
755 callback
->when
.tv_sec
= now
.tv_sec
+ time_ms
/ 1000;
756 if (callback
->when
.tv_usec
> 1000000)
758 callback
->when
.tv_usec
= callback
->when
.tv_usec
- 1000000;
759 callback
->when
.tv_sec
+= 1;
765 if((retval
= target_unregister_timer_callback(callback
->callback
, callback
->priv
)) != ERROR_OK
)
771 callback
= next_callback
;
777 int target_call_timer_callbacks(void)
779 return target_call_timer_callbacks_check_time(1);
782 /* invoke periodic callbacks immediately */
783 int target_call_timer_callbacks_now(void)
785 return target_call_timer_callbacks_check_time(0);
788 int target_alloc_working_area(struct target_s
*target
, u32 size
, working_area_t
**area
)
790 working_area_t
*c
= target
->working_areas
;
791 working_area_t
*new_wa
= NULL
;
793 /* Reevaluate working area address based on MMU state*/
794 if (target
->working_areas
== NULL
)
798 retval
= target
->type
->mmu(target
, &enabled
);
799 if (retval
!= ERROR_OK
)
805 target
->working_area
= target
->working_area_virt
;
809 target
->working_area
= target
->working_area_phys
;
813 /* only allocate multiples of 4 byte */
816 LOG_ERROR("BUG: code tried to allocate unaligned number of bytes, padding");
817 size
= CEIL(size
, 4);
820 /* see if there's already a matching working area */
823 if ((c
->free
) && (c
->size
== size
))
831 /* if not, allocate a new one */
834 working_area_t
**p
= &target
->working_areas
;
835 u32 first_free
= target
->working_area
;
836 u32 free_size
= target
->working_area_size
;
838 LOG_DEBUG("allocating new working area");
840 c
= target
->working_areas
;
843 first_free
+= c
->size
;
844 free_size
-= c
->size
;
849 if (free_size
< size
)
851 LOG_WARNING("not enough working area available(requested %d, free %d)", size
, free_size
);
852 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
855 new_wa
= malloc(sizeof(working_area_t
));
858 new_wa
->address
= first_free
;
860 if (target
->backup_working_area
)
863 new_wa
->backup
= malloc(new_wa
->size
);
864 if((retval
= target
->type
->read_memory(target
, new_wa
->address
, 4, new_wa
->size
/ 4, new_wa
->backup
)) != ERROR_OK
)
866 free(new_wa
->backup
);
873 new_wa
->backup
= NULL
;
876 /* put new entry in list */
880 /* mark as used, and return the new (reused) area */
890 int target_free_working_area_restore(struct target_s
*target
, working_area_t
*area
, int restore
)
895 if (restore
&&target
->backup_working_area
)
898 if((retval
= target
->type
->write_memory(target
, area
->address
, 4, area
->size
/ 4, area
->backup
)) != ERROR_OK
)
904 /* mark user pointer invalid */
911 int target_free_working_area(struct target_s
*target
, working_area_t
*area
)
913 return target_free_working_area_restore(target
, area
, 1);
916 /* free resources and restore memory, if restoring memory fails,
917 * free up resources anyway
919 void target_free_all_working_areas_restore(struct target_s
*target
, int restore
)
921 working_area_t
*c
= target
->working_areas
;
925 working_area_t
*next
= c
->next
;
926 target_free_working_area_restore(target
, c
, restore
);
936 target
->working_areas
= NULL
;
939 void target_free_all_working_areas(struct target_s
*target
)
941 target_free_all_working_areas_restore(target
, 1);
944 int target_register_commands(struct command_context_s
*cmd_ctx
)
947 register_command(cmd_ctx
, NULL
, "targets", handle_targets_command
, COMMAND_EXEC
, "change the current command line target (one parameter) or lists targets (with no parameter)");
948 register_command(cmd_ctx
, NULL
, "virt2phys", handle_virt2phys_command
, COMMAND_ANY
, "translate a virtual address into a physical address");
949 register_command(cmd_ctx
, NULL
, "profile", handle_profile_command
, COMMAND_EXEC
, "profiling samples the CPU PC");
951 register_jim(cmd_ctx
, "target", jim_target
, "configure target" );
954 /* script procedures */
955 register_jim(cmd_ctx
, "ocd_mem2array", jim_mem2array
, "read memory and return as a TCL array for script processing");
956 register_jim(cmd_ctx
, "ocd_array2mem", jim_array2mem
, "convert a TCL array to memory locations and write the values");
960 int target_arch_state(struct target_s
*target
)
965 LOG_USER("No target has been configured");
969 LOG_USER("target state: %s",
970 Jim_Nvp_value2name_simple(nvp_target_state
,target
->state
)->name
);
972 if (target
->state
!=TARGET_HALTED
)
975 retval
=target
->type
->arch_state(target
);
979 /* Single aligned words are guaranteed to use 16 or 32 bit access
980 * mode respectively, otherwise data is handled as quickly as
983 int target_write_buffer(struct target_s
*target
, u32 address
, u32 size
, u8
*buffer
)
986 LOG_DEBUG("writing buffer of %i byte at 0x%8.8x", size
, address
);
988 if (!target
->type
->examined
)
990 LOG_ERROR("Target not examined yet");
994 if ((address
+ size
- 1) < address
)
996 /* GDB can request this when e.g. PC is 0xfffffffc*/
997 LOG_ERROR("address+size wrapped(0x%08x, 0x%08x)", address
, size
);
1001 if (((address
% 2) == 0) && (size
== 2))
1003 return target
->type
->write_memory(target
, address
, 2, 1, buffer
);
1006 /* handle unaligned head bytes */
1009 int unaligned
= 4 - (address
% 4);
1011 if (unaligned
> size
)
1014 if ((retval
= target
->type
->write_memory(target
, address
, 1, unaligned
, buffer
)) != ERROR_OK
)
1017 buffer
+= unaligned
;
1018 address
+= unaligned
;
1022 /* handle aligned words */
1025 int aligned
= size
- (size
% 4);
1027 /* use bulk writes above a certain limit. This may have to be changed */
1030 if ((retval
= target
->type
->bulk_write_memory(target
, address
, aligned
/ 4, buffer
)) != ERROR_OK
)
1035 if ((retval
= target
->type
->write_memory(target
, address
, 4, aligned
/ 4, buffer
)) != ERROR_OK
)
1044 /* handle tail writes of less than 4 bytes */
1047 if ((retval
= target
->type
->write_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
1055 /* Single aligned words are guaranteed to use 16 or 32 bit access
1056 * mode respectively, otherwise data is handled as quickly as
1059 int target_read_buffer(struct target_s
*target
, u32 address
, u32 size
, u8
*buffer
)
1062 LOG_DEBUG("reading buffer of %i byte at 0x%8.8x", size
, address
);
1064 if (!target
->type
->examined
)
1066 LOG_ERROR("Target not examined yet");
1070 if ((address
+ size
- 1) < address
)
1072 /* GDB can request this when e.g. PC is 0xfffffffc*/
1073 LOG_ERROR("address+size wrapped(0x%08x, 0x%08x)", address
, size
);
1077 if (((address
% 2) == 0) && (size
== 2))
1079 return target
->type
->read_memory(target
, address
, 2, 1, buffer
);
1082 /* handle unaligned head bytes */
1085 int unaligned
= 4 - (address
% 4);
1087 if (unaligned
> size
)
1090 if ((retval
= target
->type
->read_memory(target
, address
, 1, unaligned
, buffer
)) != ERROR_OK
)
1093 buffer
+= unaligned
;
1094 address
+= unaligned
;
1098 /* handle aligned words */
1101 int aligned
= size
- (size
% 4);
1103 if ((retval
= target
->type
->read_memory(target
, address
, 4, aligned
/ 4, buffer
)) != ERROR_OK
)
1111 /* handle tail writes of less than 4 bytes */
1114 if ((retval
= target
->type
->read_memory(target
, address
, 1, size
, buffer
)) != ERROR_OK
)
1121 int target_checksum_memory(struct target_s
*target
, u32 address
, u32 size
, u32
* crc
)
1127 if (!target
->type
->examined
)
1129 LOG_ERROR("Target not examined yet");
1133 if ((retval
= target
->type
->checksum_memory(target
, address
,
1134 size
, &checksum
)) != ERROR_OK
)
1136 buffer
= malloc(size
);
1139 LOG_ERROR("error allocating buffer for section (%d bytes)", size
);
1140 return ERROR_INVALID_ARGUMENTS
;
1142 retval
= target_read_buffer(target
, address
, size
, buffer
);
1143 if (retval
!= ERROR_OK
)
1149 /* convert to target endianess */
1150 for (i
= 0; i
< (size
/sizeof(u32
)); i
++)
1153 target_data
= target_buffer_get_u32(target
, &buffer
[i
*sizeof(u32
)]);
1154 target_buffer_set_u32(target
, &buffer
[i
*sizeof(u32
)], target_data
);
1157 retval
= image_calculate_checksum( buffer
, size
, &checksum
);
1166 int target_blank_check_memory(struct target_s
*target
, u32 address
, u32 size
, u32
* blank
)
1169 if (!target
->type
->examined
)
1171 LOG_ERROR("Target not examined yet");
1175 if (target
->type
->blank_check_memory
== 0)
1176 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1178 retval
= target
->type
->blank_check_memory(target
, address
, size
, blank
);
1183 int target_read_u32(struct target_s
*target
, u32 address
, u32
*value
)
1186 if (!target
->type
->examined
)
1188 LOG_ERROR("Target not examined yet");
1192 int retval
= target
->type
->read_memory(target
, address
, 4, 1, value_buf
);
1194 if (retval
== ERROR_OK
)
1196 *value
= target_buffer_get_u32(target
, value_buf
);
1197 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, *value
);
1202 LOG_DEBUG("address: 0x%8.8x failed", address
);
1208 int target_read_u16(struct target_s
*target
, u32 address
, u16
*value
)
1211 if (!target
->type
->examined
)
1213 LOG_ERROR("Target not examined yet");
1217 int retval
= target
->type
->read_memory(target
, address
, 2, 1, value_buf
);
1219 if (retval
== ERROR_OK
)
1221 *value
= target_buffer_get_u16(target
, value_buf
);
1222 LOG_DEBUG("address: 0x%8.8x, value: 0x%4.4x", address
, *value
);
1227 LOG_DEBUG("address: 0x%8.8x failed", address
);
1233 int target_read_u8(struct target_s
*target
, u32 address
, u8
*value
)
1235 int retval
= target
->type
->read_memory(target
, address
, 1, 1, value
);
1236 if (!target
->type
->examined
)
1238 LOG_ERROR("Target not examined yet");
1242 if (retval
== ERROR_OK
)
1244 LOG_DEBUG("address: 0x%8.8x, value: 0x%2.2x", address
, *value
);
1249 LOG_DEBUG("address: 0x%8.8x failed", address
);
1255 int target_write_u32(struct target_s
*target
, u32 address
, u32 value
)
1259 if (!target
->type
->examined
)
1261 LOG_ERROR("Target not examined yet");
1265 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, value
);
1267 target_buffer_set_u32(target
, value_buf
, value
);
1268 if ((retval
= target
->type
->write_memory(target
, address
, 4, 1, value_buf
)) != ERROR_OK
)
1270 LOG_DEBUG("failed: %i", retval
);
1276 int target_write_u16(struct target_s
*target
, u32 address
, u16 value
)
1280 if (!target
->type
->examined
)
1282 LOG_ERROR("Target not examined yet");
1286 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address
, value
);
1288 target_buffer_set_u16(target
, value_buf
, value
);
1289 if ((retval
= target
->type
->write_memory(target
, address
, 2, 1, value_buf
)) != ERROR_OK
)
1291 LOG_DEBUG("failed: %i", retval
);
1297 int target_write_u8(struct target_s
*target
, u32 address
, u8 value
)
1300 if (!target
->type
->examined
)
1302 LOG_ERROR("Target not examined yet");
1306 LOG_DEBUG("address: 0x%8.8x, value: 0x%2.2x", address
, value
);
1308 if ((retval
= target
->type
->write_memory(target
, address
, 1, 1, &value
)) != ERROR_OK
)
1310 LOG_DEBUG("failed: %i", retval
);
1316 int target_register_user_commands(struct command_context_s
*cmd_ctx
)
1318 int retval
= ERROR_OK
;
1319 register_command(cmd_ctx
, NULL
, "reg", handle_reg_command
, COMMAND_EXEC
, "display or set a register");
1320 register_command(cmd_ctx
, NULL
, "poll", handle_poll_command
, COMMAND_EXEC
, "poll target state");
1321 register_command(cmd_ctx
, NULL
, "wait_halt", handle_wait_halt_command
, COMMAND_EXEC
, "wait for target halt [time (s)]");
1322 register_command(cmd_ctx
, NULL
, "halt", handle_halt_command
, COMMAND_EXEC
, "halt target");
1323 register_command(cmd_ctx
, NULL
, "resume", handle_resume_command
, COMMAND_EXEC
, "resume target [addr]");
1324 register_command(cmd_ctx
, NULL
, "step", handle_step_command
, COMMAND_EXEC
, "step one instruction from current PC or [addr]");
1325 register_command(cmd_ctx
, NULL
, "reset", handle_reset_command
, COMMAND_EXEC
, "reset target [run|halt|init] - default is run");
1326 register_command(cmd_ctx
, NULL
, "soft_reset_halt", handle_soft_reset_halt_command
, COMMAND_EXEC
, "halt the target and do a soft reset");
1328 register_command(cmd_ctx
, NULL
, "mdw", handle_md_command
, COMMAND_EXEC
, "display memory words <addr> [count]");
1329 register_command(cmd_ctx
, NULL
, "mdh", handle_md_command
, COMMAND_EXEC
, "display memory half-words <addr> [count]");
1330 register_command(cmd_ctx
, NULL
, "mdb", handle_md_command
, COMMAND_EXEC
, "display memory bytes <addr> [count]");
1332 register_command(cmd_ctx
, NULL
, "mww", handle_mw_command
, COMMAND_EXEC
, "write memory word <addr> <value> [count]");
1333 register_command(cmd_ctx
, NULL
, "mwh", handle_mw_command
, COMMAND_EXEC
, "write memory half-word <addr> <value> [count]");
1334 register_command(cmd_ctx
, NULL
, "mwb", handle_mw_command
, COMMAND_EXEC
, "write memory byte <addr> <value> [count]");
1336 register_command(cmd_ctx
, NULL
, "bp", handle_bp_command
, COMMAND_EXEC
, "set breakpoint <address> <length> [hw]");
1337 register_command(cmd_ctx
, NULL
, "rbp", handle_rbp_command
, COMMAND_EXEC
, "remove breakpoint <adress>");
1338 register_command(cmd_ctx
, NULL
, "wp", handle_wp_command
, COMMAND_EXEC
, "set watchpoint <address> <length> <r/w/a> [value] [mask]");
1339 register_command(cmd_ctx
, NULL
, "rwp", handle_rwp_command
, COMMAND_EXEC
, "remove watchpoint <adress>");
1341 register_command(cmd_ctx
, NULL
, "load_image", handle_load_image_command
, COMMAND_EXEC
, "load_image <file> <address> ['bin'|'ihex'|'elf'|'s19'] [min_address] [max_length]");
1342 register_command(cmd_ctx
, NULL
, "dump_image", handle_dump_image_command
, COMMAND_EXEC
, "dump_image <file> <address> <size>");
1343 register_command(cmd_ctx
, NULL
, "verify_image", handle_verify_image_command
, COMMAND_EXEC
, "verify_image <file> [offset] [type]");
1345 if((retval
= target_request_register_commands(cmd_ctx
)) != ERROR_OK
)
1347 if((retval
= trace_register_commands(cmd_ctx
)) != ERROR_OK
)
1354 int handle_targets_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1357 target_t
*target
= all_targets
;
1361 /* try as tcltarget name */
1362 for( target
= all_targets
; target
; target
= target
->next
){
1363 if( target
->cmd_name
){
1364 if( 0 == strcmp( args
[0], target
->cmd_name
) ){
1370 /* no match, try as number */
1372 int num
= strtoul(args
[0], &cp
, 0 );
1374 /* then it was not a number */
1375 command_print( cmd_ctx
, "Target: %s unknown, try one of:\n", args
[0] );
1379 target
= get_target_by_num( num
);
1380 if( target
== NULL
){
1381 command_print(cmd_ctx
,"Target: %s is unknown, try one of:\n", args
[0] );
1385 cmd_ctx
->current_target
= target
->target_number
;
1390 target
= all_targets
;
1391 command_print(cmd_ctx
, " CmdName Type Endian AbsChainPos Name State ");
1392 command_print(cmd_ctx
, "-- ---------- ---------- ---------- ----------- ------------- ----------");
1395 /* XX: abcdefghij abcdefghij abcdefghij abcdefghij */
1396 command_print(cmd_ctx
, "%2d: %-10s %-10s %-10s %10d %14s %s",
1397 target
->target_number
,
1400 Jim_Nvp_value2name_simple( nvp_target_endian
, target
->endianness
)->name
,
1401 target
->tap
->abs_chain_position
,
1402 target
->tap
->dotted_name
,
1403 Jim_Nvp_value2name_simple( nvp_target_state
, target
->state
)->name
);
1404 target
= target
->next
;
1410 // every 300ms we check for reset & powerdropout and issue a "reset halt" if
1413 static int powerDropout
;
1414 static int srstAsserted
;
1416 static int runPowerRestore
;
1417 static int runPowerDropout
;
1418 static int runSrstAsserted
;
1419 static int runSrstDeasserted
;
1421 static int sense_handler(void)
1423 static int prevSrstAsserted
= 0;
1424 static int prevPowerdropout
= 0;
1427 if ((retval
=jtag_power_dropout(&powerDropout
))!=ERROR_OK
)
1431 powerRestored
= prevPowerdropout
&& !powerDropout
;
1434 runPowerRestore
= 1;
1437 long long current
= timeval_ms();
1438 static long long lastPower
= 0;
1439 int waitMore
= lastPower
+ 2000 > current
;
1440 if (powerDropout
&& !waitMore
)
1442 runPowerDropout
= 1;
1443 lastPower
= current
;
1446 if ((retval
=jtag_srst_asserted(&srstAsserted
))!=ERROR_OK
)
1450 srstDeasserted
= prevSrstAsserted
&& !srstAsserted
;
1452 static long long lastSrst
= 0;
1453 waitMore
= lastSrst
+ 2000 > current
;
1454 if (srstDeasserted
&& !waitMore
)
1456 runSrstDeasserted
= 1;
1460 if (!prevSrstAsserted
&& srstAsserted
)
1462 runSrstAsserted
= 1;
1465 prevSrstAsserted
= srstAsserted
;
1466 prevPowerdropout
= powerDropout
;
1468 if (srstDeasserted
|| powerRestored
)
1470 /* Other than logging the event we can't do anything here.
1471 * Issuing a reset is a particularly bad idea as we might
1472 * be inside a reset already.
1480 /* process target state changes */
1481 int handle_target(void *priv
)
1483 int retval
= ERROR_OK
;
1485 /* we do not want to recurse here... */
1486 static int recursive
= 0;
1491 /* danger! running these procedures can trigger srst assertions and power dropouts.
1492 * We need to avoid an infinite loop/recursion here and we do that by
1493 * clearing the flags after running these events.
1495 int did_something
= 0;
1496 if (runSrstAsserted
)
1498 Jim_Eval( interp
, "srst_asserted");
1501 if (runSrstDeasserted
)
1503 Jim_Eval( interp
, "srst_deasserted");
1506 if (runPowerDropout
)
1508 Jim_Eval( interp
, "power_dropout");
1511 if (runPowerRestore
)
1513 Jim_Eval( interp
, "power_restore");
1519 /* clear detect flags */
1523 /* clear action flags */
1526 runSrstDeasserted
=0;
1533 target_t
*target
= all_targets
;
1538 /* only poll target if we've got power and srst isn't asserted */
1539 if (target_continous_poll
&&!powerDropout
&&!srstAsserted
)
1541 /* polling may fail silently until the target has been examined */
1542 if((retval
= target_poll(target
)) != ERROR_OK
)
1546 target
= target
->next
;
1553 int handle_reg_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1562 target
= get_current_target(cmd_ctx
);
1564 /* list all available registers for the current target */
1567 reg_cache_t
*cache
= target
->reg_cache
;
1573 for (i
= 0; i
< cache
->num_regs
; i
++)
1575 value
= buf_to_str(cache
->reg_list
[i
].value
, cache
->reg_list
[i
].size
, 16);
1576 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
);
1579 cache
= cache
->next
;
1585 /* access a single register by its ordinal number */
1586 if ((args
[0][0] >= '0') && (args
[0][0] <= '9'))
1588 int num
= strtoul(args
[0], NULL
, 0);
1589 reg_cache_t
*cache
= target
->reg_cache
;
1595 for (i
= 0; i
< cache
->num_regs
; i
++)
1599 reg
= &cache
->reg_list
[i
];
1605 cache
= cache
->next
;
1610 command_print(cmd_ctx
, "%i is out of bounds, the current target has only %i registers (0 - %i)", num
, count
, count
- 1);
1613 } else /* access a single register by its name */
1615 reg
= register_get_by_name(target
->reg_cache
, args
[0], 1);
1619 command_print(cmd_ctx
, "register %s not found in current target", args
[0]);
1624 /* display a register */
1625 if ((argc
== 1) || ((argc
== 2) && !((args
[1][0] >= '0') && (args
[1][0] <= '9'))))
1627 if ((argc
== 2) && (strcmp(args
[1], "force") == 0))
1630 if (reg
->valid
== 0)
1632 reg_arch_type_t
*arch_type
= register_get_arch_type(reg
->arch_type
);
1633 arch_type
->get(reg
);
1635 value
= buf_to_str(reg
->value
, reg
->size
, 16);
1636 command_print(cmd_ctx
, "%s (/%i): 0x%s", reg
->name
, reg
->size
, value
);
1641 /* set register value */
1644 u8
*buf
= malloc(CEIL(reg
->size
, 8));
1645 str_to_buf(args
[1], strlen(args
[1]), buf
, reg
->size
, 0);
1647 reg_arch_type_t
*arch_type
= register_get_arch_type(reg
->arch_type
);
1648 arch_type
->set(reg
, buf
);
1650 value
= buf_to_str(reg
->value
, reg
->size
, 16);
1651 command_print(cmd_ctx
, "%s (/%i): 0x%s", reg
->name
, reg
->size
, value
);
1659 command_print(cmd_ctx
, "usage: reg <#|name> [value]");
1665 int handle_poll_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1667 int retval
= ERROR_OK
;
1668 target_t
*target
= get_current_target(cmd_ctx
);
1672 if((retval
= target_poll(target
)) != ERROR_OK
)
1674 if((retval
= target_arch_state(target
)) != ERROR_OK
)
1680 if (strcmp(args
[0], "on") == 0)
1682 target_continous_poll
= 1;
1684 else if (strcmp(args
[0], "off") == 0)
1686 target_continous_poll
= 0;
1690 command_print(cmd_ctx
, "arg is \"on\" or \"off\"");
1694 return ERROR_COMMAND_SYNTAX_ERROR
;
1701 int handle_wait_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1709 ms
= strtoul(args
[0], &end
, 0) * 1000;
1712 command_print(cmd_ctx
, "usage: %s [seconds]", cmd
);
1716 target_t
*target
= get_current_target(cmd_ctx
);
1718 return target_wait_state(target
, TARGET_HALTED
, ms
);
1721 int target_wait_state(target_t
*target
, enum target_state state
, int ms
)
1724 struct timeval timeout
, now
;
1726 gettimeofday(&timeout
, NULL
);
1727 timeval_add_time(&timeout
, 0, ms
* 1000);
1731 if ((retval
=target_poll(target
))!=ERROR_OK
)
1734 if (target
->state
== state
)
1741 LOG_DEBUG("waiting for target %s...",
1742 Jim_Nvp_value2name_simple(nvp_target_state
,state
)->name
);
1745 gettimeofday(&now
, NULL
);
1746 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
) && (now
.tv_usec
>= timeout
.tv_usec
)))
1748 LOG_ERROR("timed out while waiting for target %s",
1749 Jim_Nvp_value2name_simple(nvp_target_state
,state
)->name
);
1757 int handle_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1760 target_t
*target
= get_current_target(cmd_ctx
);
1764 if ((retval
= target_halt(target
)) != ERROR_OK
)
1769 return handle_wait_halt_command(cmd_ctx
, cmd
, args
, argc
);
1772 int handle_soft_reset_halt_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1774 target_t
*target
= get_current_target(cmd_ctx
);
1776 LOG_USER("requesting target halt and executing a soft reset");
1778 target
->type
->soft_reset_halt(target
);
1783 int handle_reset_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1786 enum target_reset_mode reset_mode
= RESET_RUN
;
1790 n
= Jim_Nvp_name2value_simple( nvp_reset_modes
, args
[0] );
1791 if( (n
->name
== NULL
) || (n
->value
== RESET_UNKNOWN
) ){
1792 return ERROR_COMMAND_SYNTAX_ERROR
;
1794 reset_mode
= n
->value
;
1797 /* reset *all* targets */
1798 return target_process_reset(cmd_ctx
, reset_mode
);
1802 int handle_resume_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1805 target_t
*target
= get_current_target(cmd_ctx
);
1807 target_handle_event( target
, TARGET_EVENT_OLD_pre_resume
);
1810 retval
= target_resume(target
, 1, 0, 1, 0); /* current pc, addr = 0, handle breakpoints, not debugging */
1812 retval
= target_resume(target
, 0, strtoul(args
[0], NULL
, 0), 1, 0); /* addr = args[0], handle breakpoints, not debugging */
1815 retval
= ERROR_COMMAND_SYNTAX_ERROR
;
1821 int handle_step_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1823 target_t
*target
= get_current_target(cmd_ctx
);
1828 return target
->type
->step(target
, 1, 0, 1); /* current pc, addr = 0, handle breakpoints */
1831 return target
->type
->step(target
, 0, strtoul(args
[0], NULL
, 0), 1); /* addr = args[0], handle breakpoints */
1836 int handle_md_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1838 const int line_bytecnt
= 32;
1851 target_t
*target
= get_current_target(cmd_ctx
);
1857 count
= strtoul(args
[1], NULL
, 0);
1859 address
= strtoul(args
[0], NULL
, 0);
1865 size
= 4; line_modulo
= line_bytecnt
/ 4;
1868 size
= 2; line_modulo
= line_bytecnt
/ 2;
1871 size
= 1; line_modulo
= line_bytecnt
/ 1;
1877 buffer
= calloc(count
, size
);
1878 retval
= target
->type
->read_memory(target
, address
, size
, count
, buffer
);
1879 if (retval
== ERROR_OK
)
1883 for (i
= 0; i
< count
; i
++)
1885 if (i
%line_modulo
== 0)
1886 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "0x%8.8x: ", address
+ (i
*size
));
1891 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%8.8x ", target_buffer_get_u32(target
, &buffer
[i
*4]));
1894 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%4.4x ", target_buffer_get_u16(target
, &buffer
[i
*2]));
1897 output_len
+= snprintf(output
+ output_len
, 128 - output_len
, "%2.2x ", buffer
[i
*1]);
1901 if ((i
%line_modulo
== line_modulo
-1) || (i
== count
- 1))
1903 command_print(cmd_ctx
, output
);
1914 int handle_mw_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1921 target_t
*target
= get_current_target(cmd_ctx
);
1924 if ((argc
< 2) || (argc
> 3))
1925 return ERROR_COMMAND_SYNTAX_ERROR
;
1927 address
= strtoul(args
[0], NULL
, 0);
1928 value
= strtoul(args
[1], NULL
, 0);
1930 count
= strtoul(args
[2], NULL
, 0);
1936 target_buffer_set_u32(target
, value_buf
, value
);
1940 target_buffer_set_u16(target
, value_buf
, value
);
1944 value_buf
[0] = value
;
1947 return ERROR_COMMAND_SYNTAX_ERROR
;
1949 for (i
=0; i
<count
; i
++)
1955 retval
= target
->type
->write_memory(target
, address
+ i
*wordsize
, 4, 1, value_buf
);
1958 retval
= target
->type
->write_memory(target
, address
+ i
*wordsize
, 2, 1, value_buf
);
1961 retval
= target
->type
->write_memory(target
, address
+ i
*wordsize
, 1, 1, value_buf
);
1968 if (retval
!=ERROR_OK
)
1978 int handle_load_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
1984 u32 max_address
=0xffffffff;
1986 int retval
, retvaltemp
;
1990 duration_t duration
;
1991 char *duration_text
;
1993 target_t
*target
= get_current_target(cmd_ctx
);
1995 if ((argc
< 1)||(argc
> 5))
1997 return ERROR_COMMAND_SYNTAX_ERROR
;
2000 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
2003 image
.base_address_set
= 1;
2004 image
.base_address
= strtoul(args
[1], NULL
, 0);
2008 image
.base_address_set
= 0;
2012 image
.start_address_set
= 0;
2016 min_address
=strtoul(args
[3], NULL
, 0);
2020 max_address
=strtoul(args
[4], NULL
, 0)+min_address
;
2023 if (min_address
>max_address
)
2025 return ERROR_COMMAND_SYNTAX_ERROR
;
2029 duration_start_measure(&duration
);
2031 if (image_open(&image
, args
[0], (argc
>= 3) ? args
[2] : NULL
) != ERROR_OK
)
2038 for (i
= 0; i
< image
.num_sections
; i
++)
2040 buffer
= malloc(image
.sections
[i
].size
);
2043 command_print(cmd_ctx
, "error allocating buffer for section (%d bytes)", image
.sections
[i
].size
);
2047 if ((retval
= image_read_section(&image
, i
, 0x0, image
.sections
[i
].size
, buffer
, &buf_cnt
)) != ERROR_OK
)
2057 /* DANGER!!! beware of unsigned comparision here!!! */
2059 if ((image
.sections
[i
].base_address
+buf_cnt
>=min_address
)&&
2060 (image
.sections
[i
].base_address
<max_address
))
2062 if (image
.sections
[i
].base_address
<min_address
)
2064 /* clip addresses below */
2065 offset
+=min_address
-image
.sections
[i
].base_address
;
2069 if (image
.sections
[i
].base_address
+buf_cnt
>max_address
)
2071 length
-=(image
.sections
[i
].base_address
+buf_cnt
)-max_address
;
2074 if ((retval
= target_write_buffer(target
, image
.sections
[i
].base_address
+offset
, length
, buffer
+offset
)) != ERROR_OK
)
2079 image_size
+= length
;
2080 command_print(cmd_ctx
, "%u byte written at address 0x%8.8x", length
, image
.sections
[i
].base_address
+offset
);
2086 if((retvaltemp
= duration_stop_measure(&duration
, &duration_text
)) != ERROR_OK
)
2088 image_close(&image
);
2092 if (retval
==ERROR_OK
)
2094 command_print(cmd_ctx
, "downloaded %u byte in %s", image_size
, duration_text
);
2096 free(duration_text
);
2098 image_close(&image
);
2104 int handle_dump_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2111 int retval
=ERROR_OK
, retvaltemp
;
2113 duration_t duration
;
2114 char *duration_text
;
2116 target_t
*target
= get_current_target(cmd_ctx
);
2120 command_print(cmd_ctx
, "usage: dump_image <filename> <address> <size>");
2124 address
= strtoul(args
[1], NULL
, 0);
2125 size
= strtoul(args
[2], NULL
, 0);
2127 if ((address
& 3) || (size
& 3))
2129 command_print(cmd_ctx
, "only 32-bit aligned address and size are supported");
2133 if (fileio_open(&fileio
, args
[0], FILEIO_WRITE
, FILEIO_BINARY
) != ERROR_OK
)
2138 duration_start_measure(&duration
);
2143 u32 this_run_size
= (size
> 560) ? 560 : size
;
2145 retval
= target
->type
->read_memory(target
, address
, 4, this_run_size
/ 4, buffer
);
2146 if (retval
!= ERROR_OK
)
2151 retval
= fileio_write(&fileio
, this_run_size
, buffer
, &size_written
);
2152 if (retval
!= ERROR_OK
)
2157 size
-= this_run_size
;
2158 address
+= this_run_size
;
2161 if((retvaltemp
= fileio_close(&fileio
)) != ERROR_OK
)
2164 if((retvaltemp
= duration_stop_measure(&duration
, &duration_text
)) != ERROR_OK
)
2167 if (retval
==ERROR_OK
)
2169 command_print(cmd_ctx
, "dumped %"PRIi64
" byte in %s", fileio
.size
, duration_text
);
2171 free(duration_text
);
2176 int handle_verify_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2182 int retval
, retvaltemp
;
2184 u32 mem_checksum
= 0;
2188 duration_t duration
;
2189 char *duration_text
;
2191 target_t
*target
= get_current_target(cmd_ctx
);
2195 return ERROR_COMMAND_SYNTAX_ERROR
;
2200 LOG_ERROR("no target selected");
2204 duration_start_measure(&duration
);
2208 image
.base_address_set
= 1;
2209 image
.base_address
= strtoul(args
[1], NULL
, 0);
2213 image
.base_address_set
= 0;
2214 image
.base_address
= 0x0;
2217 image
.start_address_set
= 0;
2219 if ((retval
=image_open(&image
, args
[0], (argc
== 3) ? args
[2] : NULL
)) != ERROR_OK
)
2226 for (i
= 0; i
< image
.num_sections
; i
++)
2228 buffer
= malloc(image
.sections
[i
].size
);
2231 command_print(cmd_ctx
, "error allocating buffer for section (%d bytes)", image
.sections
[i
].size
);
2234 if ((retval
= image_read_section(&image
, i
, 0x0, image
.sections
[i
].size
, buffer
, &buf_cnt
)) != ERROR_OK
)
2240 /* calculate checksum of image */
2241 image_calculate_checksum( buffer
, buf_cnt
, &checksum
);
2243 retval
= target_checksum_memory(target
, image
.sections
[i
].base_address
, buf_cnt
, &mem_checksum
);
2244 if( retval
!= ERROR_OK
)
2250 if( checksum
!= mem_checksum
)
2252 /* failed crc checksum, fall back to a binary compare */
2255 command_print(cmd_ctx
, "checksum mismatch - attempting binary compare");
2257 data
= (u8
*)malloc(buf_cnt
);
2259 /* Can we use 32bit word accesses? */
2261 int count
= buf_cnt
;
2262 if ((count
% 4) == 0)
2267 retval
= target
->type
->read_memory(target
, image
.sections
[i
].base_address
, size
, count
, data
);
2268 if (retval
== ERROR_OK
)
2271 for (t
= 0; t
< buf_cnt
; t
++)
2273 if (data
[t
] != buffer
[t
])
2275 command_print(cmd_ctx
, "Verify operation failed address 0x%08x. Was 0x%02x instead of 0x%02x\n", t
+ image
.sections
[i
].base_address
, data
[t
], buffer
[t
]);
2292 image_size
+= buf_cnt
;
2296 if((retvaltemp
= duration_stop_measure(&duration
, &duration_text
)) != ERROR_OK
)
2298 image_close(&image
);
2302 if (retval
==ERROR_OK
)
2304 command_print(cmd_ctx
, "verified %u bytes in %s", image_size
, duration_text
);
2306 free(duration_text
);
2308 image_close(&image
);
2313 int handle_bp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2316 target_t
*target
= get_current_target(cmd_ctx
);
2320 breakpoint_t
*breakpoint
= target
->breakpoints
;
2324 if (breakpoint
->type
== BKPT_SOFT
)
2326 char* buf
= buf_to_str(breakpoint
->orig_instr
, breakpoint
->length
, 16);
2327 command_print(cmd_ctx
, "0x%8.8x, 0x%x, %i, 0x%s", breakpoint
->address
, breakpoint
->length
, breakpoint
->set
, buf
);
2332 command_print(cmd_ctx
, "0x%8.8x, 0x%x, %i", breakpoint
->address
, breakpoint
->length
, breakpoint
->set
);
2334 breakpoint
= breakpoint
->next
;
2342 length
= strtoul(args
[1], NULL
, 0);
2345 if (strcmp(args
[2], "hw") == 0)
2348 if ((retval
= breakpoint_add(target
, strtoul(args
[0], NULL
, 0), length
, hw
)) != ERROR_OK
)
2350 LOG_ERROR("Failure setting breakpoints");
2354 command_print(cmd_ctx
, "breakpoint added at address 0x%8.8x", strtoul(args
[0], NULL
, 0));
2359 command_print(cmd_ctx
, "usage: bp <address> <length> ['hw']");
2365 int handle_rbp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2367 target_t
*target
= get_current_target(cmd_ctx
);
2370 breakpoint_remove(target
, strtoul(args
[0], NULL
, 0));
2375 int handle_wp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2377 target_t
*target
= get_current_target(cmd_ctx
);
2382 watchpoint_t
*watchpoint
= target
->watchpoints
;
2386 command_print(cmd_ctx
, "address: 0x%8.8x, len: 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
);
2387 watchpoint
= watchpoint
->next
;
2392 enum watchpoint_rw type
= WPT_ACCESS
;
2393 u32 data_value
= 0x0;
2394 u32 data_mask
= 0xffffffff;
2410 command_print(cmd_ctx
, "usage: wp <address> <length> [r/w/a] [value] [mask]");
2416 data_value
= strtoul(args
[3], NULL
, 0);
2420 data_mask
= strtoul(args
[4], NULL
, 0);
2423 if ((retval
= watchpoint_add(target
, strtoul(args
[0], NULL
, 0),
2424 strtoul(args
[1], NULL
, 0), type
, data_value
, data_mask
)) != ERROR_OK
)
2426 LOG_ERROR("Failure setting breakpoints");
2431 command_print(cmd_ctx
, "usage: wp <address> <length> [r/w/a] [value] [mask]");
2437 int handle_rwp_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2439 target_t
*target
= get_current_target(cmd_ctx
);
2442 watchpoint_remove(target
, strtoul(args
[0], NULL
, 0));
2447 int handle_virt2phys_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2450 target_t
*target
= get_current_target(cmd_ctx
);
2456 return ERROR_COMMAND_SYNTAX_ERROR
;
2458 va
= strtoul(args
[0], NULL
, 0);
2460 retval
= target
->type
->virt2phys(target
, va
, &pa
);
2461 if (retval
== ERROR_OK
)
2463 command_print(cmd_ctx
, "Physical address 0x%08x", pa
);
2467 /* lower levels will have logged a detailed error which is
2468 * forwarded to telnet/GDB session.
2473 static void writeLong(FILE *f
, int l
)
2478 char c
=(l
>>(i
*8))&0xff;
2479 fwrite(&c
, 1, 1, f
);
2483 static void writeString(FILE *f
, char *s
)
2485 fwrite(s
, 1, strlen(s
), f
);
2490 // Dump a gmon.out histogram file.
2491 static void writeGmon(u32
*samples
, int sampleNum
, char *filename
)
2494 FILE *f
=fopen(filename
, "w");
2497 fwrite("gmon", 1, 4, f
);
2498 writeLong(f
, 0x00000001); // Version
2499 writeLong(f
, 0); // padding
2500 writeLong(f
, 0); // padding
2501 writeLong(f
, 0); // padding
2503 fwrite("", 1, 1, f
); // GMON_TAG_TIME_HIST
2505 // figure out bucket size
2508 for (i
=0; i
<sampleNum
; i
++)
2520 int addressSpace
=(max
-min
+1);
2522 static int const maxBuckets
=256*1024; // maximum buckets.
2523 int length
=addressSpace
;
2524 if (length
> maxBuckets
)
2528 int *buckets
=malloc(sizeof(int)*length
);
2534 memset(buckets
, 0, sizeof(int)*length
);
2535 for (i
=0; i
<sampleNum
;i
++)
2537 u32 address
=samples
[i
];
2538 long long a
=address
-min
;
2539 long long b
=length
-1;
2540 long long c
=addressSpace
-1;
2541 int index
=(a
*b
)/c
; // danger!!!! int32 overflows
2545 // append binary memory gmon.out &profile_hist_hdr ((char*)&profile_hist_hdr + sizeof(struct gmon_hist_hdr))
2546 writeLong(f
, min
); // low_pc
2547 writeLong(f
, max
); // high_pc
2548 writeLong(f
, length
); // # of samples
2549 writeLong(f
, 64000000); // 64MHz
2550 writeString(f
, "seconds");
2551 for (i
=0; i
<(15-strlen("seconds")); i
++)
2553 fwrite("", 1, 1, f
); // padding
2555 writeString(f
, "s");
2557 // append binary memory gmon.out profile_hist_data (profile_hist_data + profile_hist_hdr.hist_size)
2559 char *data
=malloc(2*length
);
2562 for (i
=0; i
<length
;i
++)
2571 data
[i
*2+1]=(val
>>8)&0xff;
2574 fwrite(data
, 1, length
*2, f
);
2584 /* profiling samples the CPU PC as quickly as OpenOCD is able, which will be used as a random sampling of PC */
2585 int handle_profile_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2587 target_t
*target
= get_current_target(cmd_ctx
);
2588 struct timeval timeout
, now
;
2590 gettimeofday(&timeout
, NULL
);
2593 return ERROR_COMMAND_SYNTAX_ERROR
;
2596 timeval_add_time(&timeout
, strtoul(args
[0], &end
, 0), 0);
2602 command_print(cmd_ctx
, "Starting profiling. Halting and resuming the target as often as we can...");
2604 static const int maxSample
=10000;
2605 u32
*samples
=malloc(sizeof(u32
)*maxSample
);
2610 int retval
=ERROR_OK
;
2611 // hopefully it is safe to cache! We want to stop/restart as quickly as possible.
2612 reg_t
*reg
= register_get_by_name(target
->reg_cache
, "pc", 1);
2616 target_poll(target
);
2617 if (target
->state
== TARGET_HALTED
)
2619 u32 t
=*((u32
*)reg
->value
);
2620 samples
[numSamples
++]=t
;
2621 retval
= target_resume(target
, 1, 0, 0, 0); /* current pc, addr = 0, do not handle breakpoints, not debugging */
2622 target_poll(target
);
2623 alive_sleep(10); // sleep 10ms, i.e. <100 samples/second.
2624 } else if (target
->state
== TARGET_RUNNING
)
2626 // We want to quickly sample the PC.
2627 if((retval
= target_halt(target
)) != ERROR_OK
)
2634 command_print(cmd_ctx
, "Target not halted or running");
2638 if (retval
!=ERROR_OK
)
2643 gettimeofday(&now
, NULL
);
2644 if ((numSamples
>=maxSample
) || ((now
.tv_sec
>= timeout
.tv_sec
) && (now
.tv_usec
>= timeout
.tv_usec
)))
2646 command_print(cmd_ctx
, "Profiling completed. %d samples.", numSamples
);
2647 if((retval
= target_poll(target
)) != ERROR_OK
)
2652 if (target
->state
== TARGET_HALTED
)
2654 target_resume(target
, 1, 0, 0, 0); /* current pc, addr = 0, do not handle breakpoints, not debugging */
2656 if((retval
= target_poll(target
)) != ERROR_OK
)
2661 writeGmon(samples
, numSamples
, args
[1]);
2662 command_print(cmd_ctx
, "Wrote %s", args
[1]);
2671 static int new_int_array_element(Jim_Interp
* interp
, const char *varname
, int idx
, u32 val
)
2674 Jim_Obj
*nameObjPtr
, *valObjPtr
;
2677 namebuf
= alloc_printf("%s(%d)", varname
, idx
);
2681 nameObjPtr
= Jim_NewStringObj(interp
, namebuf
, -1);
2682 valObjPtr
= Jim_NewIntObj(interp
, val
);
2683 if (!nameObjPtr
|| !valObjPtr
)
2689 Jim_IncrRefCount(nameObjPtr
);
2690 Jim_IncrRefCount(valObjPtr
);
2691 result
= Jim_SetVariable(interp
, nameObjPtr
, valObjPtr
);
2692 Jim_DecrRefCount(interp
, nameObjPtr
);
2693 Jim_DecrRefCount(interp
, valObjPtr
);
2695 /* printf("%s(%d) <= 0%08x\n", varname, idx, val); */
2699 static int jim_mem2array(Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
)
2701 command_context_t
*context
;
2704 context
= Jim_GetAssocData(interp
, "context");
2705 if (context
== NULL
)
2707 LOG_ERROR("mem2array: no command context");
2710 target
= get_current_target(context
);
2713 LOG_ERROR("mem2array: no current target");
2717 return target_mem2array(interp
, target
, argc
,argv
);
2720 static int target_mem2array(Jim_Interp
*interp
, target_t
*target
, int argc
, Jim_Obj
*const *argv
)
2728 const char *varname
;
2730 int i
, n
, e
, retval
;
2732 /* argv[1] = name of array to receive the data
2733 * argv[2] = desired width
2734 * argv[3] = memory address
2735 * argv[4] = count of times to read
2738 Jim_WrongNumArgs(interp
, 1, argv
, "varname width addr nelems");
2741 varname
= Jim_GetString(argv
[1], &len
);
2742 /* given "foo" get space for worse case "foo(%d)" .. add 20 */
2744 e
= Jim_GetLong(interp
, argv
[2], &l
);
2750 e
= Jim_GetLong(interp
, argv
[3], &l
);
2755 e
= Jim_GetLong(interp
, argv
[4], &l
);
2771 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2772 Jim_AppendStrings( interp
, Jim_GetResult(interp
), "Invalid width param, must be 8/16/32", NULL
);
2776 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2777 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "mem2array: zero width read?", NULL
);
2780 if ((addr
+ (len
* width
)) < addr
) {
2781 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2782 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "mem2array: addr + len - wraps to zero?", NULL
);
2785 /* absurd transfer size? */
2787 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2788 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "mem2array: absurd > 64K item request", NULL
);
2793 ((width
== 2) && ((addr
& 1) == 0)) ||
2794 ((width
== 4) && ((addr
& 3) == 0))) {
2798 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2799 sprintf(buf
, "mem2array address: 0x%08x is not aligned for %d byte reads", addr
, width
);
2800 Jim_AppendStrings(interp
, Jim_GetResult(interp
), buf
, NULL
);
2811 /* Slurp... in buffer size chunks */
2813 count
= len
; /* in objects.. */
2814 if (count
> (sizeof(buffer
)/width
)) {
2815 count
= (sizeof(buffer
)/width
);
2818 retval
= target
->type
->read_memory( target
, addr
, width
, count
, buffer
);
2819 if (retval
!= ERROR_OK
) {
2821 LOG_ERROR("mem2array: Read @ 0x%08x, w=%d, cnt=%d, failed", addr
, width
, count
);
2822 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2823 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "mem2array: cannot read memory", NULL
);
2827 v
= 0; /* shut up gcc */
2828 for (i
= 0 ;i
< count
;i
++, n
++) {
2831 v
= target_buffer_get_u32(target
, &buffer
[i
*width
]);
2834 v
= target_buffer_get_u16(target
, &buffer
[i
*width
]);
2837 v
= buffer
[i
] & 0x0ff;
2840 new_int_array_element(interp
, varname
, n
, v
);
2846 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2851 static int get_int_array_element(Jim_Interp
* interp
, const char *varname
, int idx
, u32
*val
)
2854 Jim_Obj
*nameObjPtr
, *valObjPtr
;
2858 namebuf
= alloc_printf("%s(%d)", varname
, idx
);
2862 nameObjPtr
= Jim_NewStringObj(interp
, namebuf
, -1);
2869 Jim_IncrRefCount(nameObjPtr
);
2870 valObjPtr
= Jim_GetVariable(interp
, nameObjPtr
, JIM_ERRMSG
);
2871 Jim_DecrRefCount(interp
, nameObjPtr
);
2873 if (valObjPtr
== NULL
)
2876 result
= Jim_GetLong(interp
, valObjPtr
, &l
);
2877 /* printf("%s(%d) => 0%08x\n", varname, idx, val); */
2882 static int jim_array2mem(Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
)
2884 command_context_t
*context
;
2887 context
= Jim_GetAssocData(interp
, "context");
2888 if (context
== NULL
){
2889 LOG_ERROR("array2mem: no command context");
2892 target
= get_current_target(context
);
2893 if (target
== NULL
){
2894 LOG_ERROR("array2mem: no current target");
2898 return target_array2mem( interp
,target
, argc
, argv
);
2902 static int target_array2mem(Jim_Interp
*interp
, target_t
*target
, int argc
, Jim_Obj
*const *argv
)
2910 const char *varname
;
2912 int i
, n
, e
, retval
;
2914 /* argv[1] = name of array to get the data
2915 * argv[2] = desired width
2916 * argv[3] = memory address
2917 * argv[4] = count to write
2920 Jim_WrongNumArgs(interp
, 1, argv
, "varname width addr nelems");
2923 varname
= Jim_GetString(argv
[1], &len
);
2924 /* given "foo" get space for worse case "foo(%d)" .. add 20 */
2926 e
= Jim_GetLong(interp
, argv
[2], &l
);
2932 e
= Jim_GetLong(interp
, argv
[3], &l
);
2937 e
= Jim_GetLong(interp
, argv
[4], &l
);
2953 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2954 Jim_AppendStrings( interp
, Jim_GetResult(interp
), "Invalid width param, must be 8/16/32", NULL
);
2958 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2959 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "array2mem: zero width read?", NULL
);
2962 if ((addr
+ (len
* width
)) < addr
) {
2963 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2964 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "array2mem: addr + len - wraps to zero?", NULL
);
2967 /* absurd transfer size? */
2969 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2970 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "array2mem: absurd > 64K item request", NULL
);
2975 ((width
== 2) && ((addr
& 1) == 0)) ||
2976 ((width
== 4) && ((addr
& 3) == 0))) {
2980 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
2981 sprintf(buf
, "array2mem address: 0x%08x is not aligned for %d byte reads", addr
, width
);
2982 Jim_AppendStrings(interp
, Jim_GetResult(interp
), buf
, NULL
);
2994 /* Slurp... in buffer size chunks */
2996 count
= len
; /* in objects.. */
2997 if (count
> (sizeof(buffer
)/width
)) {
2998 count
= (sizeof(buffer
)/width
);
3001 v
= 0; /* shut up gcc */
3002 for (i
= 0 ;i
< count
;i
++, n
++) {
3003 get_int_array_element(interp
, varname
, n
, &v
);
3006 target_buffer_set_u32(target
, &buffer
[i
*width
], v
);
3009 target_buffer_set_u16(target
, &buffer
[i
*width
], v
);
3012 buffer
[i
] = v
& 0x0ff;
3018 retval
= target
->type
->write_memory(target
, addr
, width
, count
, buffer
);
3019 if (retval
!= ERROR_OK
) {
3021 LOG_ERROR("array2mem: Write @ 0x%08x, w=%d, cnt=%d, failed", addr
, width
, count
);
3022 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
3023 Jim_AppendStrings(interp
, Jim_GetResult(interp
), "array2mem: cannot read memory", NULL
);
3029 Jim_SetResult(interp
, Jim_NewEmptyStringObj(interp
));
3035 target_all_handle_event( enum target_event e
)
3040 LOG_DEBUG( "**all*targets: event: %d, %s",
3042 Jim_Nvp_value2name_simple( nvp_target_event
, e
)->name
);
3044 target
= all_targets
;
3046 target_handle_event( target
, e
);
3047 target
= target
->next
;
3052 target_handle_event( target_t
*target
, enum target_event e
)
3054 target_event_action_t
*teap
;
3057 teap
= target
->event_action
;
3061 if( teap
->event
== e
){
3063 LOG_DEBUG( "target: (%d) %s (%s) event: %d (%s) action: %s\n",
3064 target
->target_number
,
3068 Jim_Nvp_value2name_simple( nvp_target_event
, e
)->name
,
3069 Jim_GetString( teap
->body
, NULL
) );
3070 if (Jim_EvalObj( interp
, teap
->body
)!=JIM_OK
)
3072 Jim_PrintErrorMessage(interp
);
3078 LOG_DEBUG( "event: %d %s - no action",
3080 Jim_Nvp_value2name_simple( nvp_target_event
, e
)->name
);
3084 enum target_cfg_param
{
3087 TCFG_WORK_AREA_VIRT
,
3088 TCFG_WORK_AREA_PHYS
,
3089 TCFG_WORK_AREA_SIZE
,
3090 TCFG_WORK_AREA_BACKUP
,
3093 TCFG_CHAIN_POSITION
,
3097 static Jim_Nvp nvp_config_opts
[] = {
3098 { .name
= "-type", .value
= TCFG_TYPE
},
3099 { .name
= "-event", .value
= TCFG_EVENT
},
3100 { .name
= "-work-area-virt", .value
= TCFG_WORK_AREA_VIRT
},
3101 { .name
= "-work-area-phys", .value
= TCFG_WORK_AREA_PHYS
},
3102 { .name
= "-work-area-size", .value
= TCFG_WORK_AREA_SIZE
},
3103 { .name
= "-work-area-backup", .value
= TCFG_WORK_AREA_BACKUP
},
3104 { .name
= "-endian" , .value
= TCFG_ENDIAN
},
3105 { .name
= "-variant", .value
= TCFG_VARIANT
},
3106 { .name
= "-chain-position", .value
= TCFG_CHAIN_POSITION
},
3108 { .name
= NULL
, .value
= -1 }
3113 target_configure( Jim_GetOptInfo
*goi
,
3123 /* parse config or cget options ... */
3124 while( goi
->argc
> 0 ){
3125 Jim_SetEmptyResult( goi
->interp
);
3126 //Jim_GetOpt_Debug( goi );
3128 if( target
->type
->target_jim_configure
){
3129 /* target defines a configure function */
3130 /* target gets first dibs on parameters */
3131 e
= (*(target
->type
->target_jim_configure
))( target
, goi
);
3140 /* otherwise we 'continue' below */
3142 e
= Jim_GetOpt_Nvp( goi
, nvp_config_opts
, &n
);
3144 Jim_GetOpt_NvpUnknown( goi
, nvp_config_opts
, 0 );
3150 if( goi
->isconfigure
){
3151 Jim_SetResult_sprintf( goi
->interp
, "not setable: %s", n
->name
);
3155 if( goi
->argc
!= 0 ){
3156 Jim_WrongNumArgs( goi
->interp
, goi
->argc
, goi
->argv
, "NO PARAMS");
3160 Jim_SetResultString( goi
->interp
, target
->type
->name
, -1 );
3164 if( goi
->argc
== 0 ){
3165 Jim_WrongNumArgs( goi
->interp
, goi
->argc
, goi
->argv
, "-event ?event-name? ...");
3169 e
= Jim_GetOpt_Nvp( goi
, nvp_target_event
, &n
);
3171 Jim_GetOpt_NvpUnknown( goi
, nvp_target_event
, 1 );
3175 if( goi
->isconfigure
){
3176 if( goi
->argc
!= 1 ){
3177 Jim_WrongNumArgs( goi
->interp
, goi
->argc
, goi
->argv
, "-event ?event-name? ?EVENT-BODY?");
3181 if( goi
->argc
!= 0 ){
3182 Jim_WrongNumArgs(goi
->interp
, goi
->argc
, goi
->argv
, "-event ?event-name?");
3189 target_event_action_t
*teap
;
3191 teap
= target
->event_action
;
3192 /* replace existing? */
3194 if( teap
->event
== n
->value
){
3200 if( goi
->isconfigure
){
3203 teap
= calloc( 1, sizeof(*teap
) );
3205 teap
->event
= n
->value
;
3206 Jim_GetOpt_Obj( goi
, &o
);
3208 Jim_DecrRefCount( interp
, teap
->body
);
3210 teap
->body
= Jim_DuplicateObj( goi
->interp
, o
);
3213 * Tcl/TK - "tk events" have a nice feature.
3214 * See the "BIND" command.
3215 * We should support that here.
3216 * You can specify %X and %Y in the event code.
3217 * The idea is: %T - target name.
3218 * The idea is: %N - target number
3219 * The idea is: %E - event name.
3221 Jim_IncrRefCount( teap
->body
);
3223 /* add to head of event list */
3224 teap
->next
= target
->event_action
;
3225 target
->event_action
= teap
;
3226 Jim_SetEmptyResult(goi
->interp
);
3230 Jim_SetEmptyResult( goi
->interp
);
3232 Jim_SetResult( goi
->interp
, Jim_DuplicateObj( goi
->interp
, teap
->body
) );
3239 case TCFG_WORK_AREA_VIRT
:
3240 if( goi
->isconfigure
){
3241 target_free_all_working_areas(target
);
3242 e
= Jim_GetOpt_Wide( goi
, &w
);
3246 target
->working_area_virt
= w
;
3248 if( goi
->argc
!= 0 ){
3252 Jim_SetResult( interp
, Jim_NewIntObj( goi
->interp
, target
->working_area_virt
) );
3256 case TCFG_WORK_AREA_PHYS
:
3257 if( goi
->isconfigure
){
3258 target_free_all_working_areas(target
);
3259 e
= Jim_GetOpt_Wide( goi
, &w
);
3263 target
->working_area_phys
= w
;
3265 if( goi
->argc
!= 0 ){
3269 Jim_SetResult( interp
, Jim_NewIntObj( goi
->interp
, target
->working_area_phys
) );
3273 case TCFG_WORK_AREA_SIZE
:
3274 if( goi
->isconfigure
){
3275 target_free_all_working_areas(target
);
3276 e
= Jim_GetOpt_Wide( goi
, &w
);
3280 target
->working_area_size
= w
;
3282 if( goi
->argc
!= 0 ){
3286 Jim_SetResult( interp
, Jim_NewIntObj( goi
->interp
, target
->working_area_size
) );
3290 case TCFG_WORK_AREA_BACKUP
:
3291 if( goi
->isconfigure
){
3292 target_free_all_working_areas(target
);
3293 e
= Jim_GetOpt_Wide( goi
, &w
);
3297 /* make this exactly 1 or 0 */
3298 target
->backup_working_area
= (!!w
);
3300 if( goi
->argc
!= 0 ){
3304 Jim_SetResult( interp
, Jim_NewIntObj( goi
->interp
, target
->working_area_size
) );
3305 /* loop for more e*/
3309 if( goi
->isconfigure
){
3310 e
= Jim_GetOpt_Nvp( goi
, nvp_target_endian
, &n
);
3312 Jim_GetOpt_NvpUnknown( goi
, nvp_target_endian
, 1 );
3315 target
->endianness
= n
->value
;
3317 if( goi
->argc
!= 0 ){
3321 n
= Jim_Nvp_value2name_simple( nvp_target_endian
, target
->endianness
);
3322 if( n
->name
== NULL
){
3323 target
->endianness
= TARGET_LITTLE_ENDIAN
;
3324 n
= Jim_Nvp_value2name_simple( nvp_target_endian
, target
->endianness
);
3326 Jim_SetResultString( goi
->interp
, n
->name
, -1 );
3331 if( goi
->isconfigure
){
3332 if( goi
->argc
< 1 ){
3333 Jim_SetResult_sprintf( goi
->interp
,
3338 if( target
->variant
){
3339 free((void *)(target
->variant
));
3341 e
= Jim_GetOpt_String( goi
, &cp
, NULL
);
3342 target
->variant
= strdup(cp
);
3344 if( goi
->argc
!= 0 ){
3348 Jim_SetResultString( goi
->interp
, target
->variant
,-1 );
3351 case TCFG_CHAIN_POSITION
:
3352 if( goi
->isconfigure
){
3355 target_free_all_working_areas(target
);
3356 e
= Jim_GetOpt_Obj( goi
, &o
);
3360 tap
= jtag_TapByJimObj( goi
->interp
, o
);
3364 /* make this exactly 1 or 0 */
3367 if( goi
->argc
!= 0 ){
3371 Jim_SetResultString( interp
, target
->tap
->dotted_name
, -1 );
3372 /* loop for more e*/
3375 } /* while( goi->argc ) */
3376 /* done - we return */
3381 /** this is the 'tcl' handler for the target specific command */
3383 tcl_target_func( Jim_Interp
*interp
,
3385 Jim_Obj
*const *argv
)
3393 struct command_context_s
*cmd_ctx
;
3401 TS_CMD_MWW
, TS_CMD_MWH
, TS_CMD_MWB
,
3402 TS_CMD_MDW
, TS_CMD_MDH
, TS_CMD_MDB
,
3403 TS_CMD_MRW
, TS_CMD_MRH
, TS_CMD_MRB
,
3404 TS_CMD_MEM2ARRAY
, TS_CMD_ARRAY2MEM
,
3412 TS_CMD_INVOKE_EVENT
,
3415 static const Jim_Nvp target_options
[] = {
3416 { .name
= "configure", .value
= TS_CMD_CONFIGURE
},
3417 { .name
= "cget", .value
= TS_CMD_CGET
},
3418 { .name
= "mww", .value
= TS_CMD_MWW
},
3419 { .name
= "mwh", .value
= TS_CMD_MWH
},
3420 { .name
= "mwb", .value
= TS_CMD_MWB
},
3421 { .name
= "mdw", .value
= TS_CMD_MDW
},
3422 { .name
= "mdh", .value
= TS_CMD_MDH
},
3423 { .name
= "mdb", .value
= TS_CMD_MDB
},
3424 { .name
= "mem2array", .value
= TS_CMD_MEM2ARRAY
},
3425 { .name
= "array2mem", .value
= TS_CMD_ARRAY2MEM
},
3426 { .name
= "eventlist", .value
= TS_CMD_EVENTLIST
},
3427 { .name
= "curstate", .value
= TS_CMD_CURSTATE
},
3429 { .name
= "arp_examine", .value
= TS_CMD_EXAMINE
},
3430 { .name
= "arp_poll", .value
= TS_CMD_POLL
},
3431 { .name
= "arp_reset", .value
= TS_CMD_RESET
},
3432 { .name
= "arp_halt", .value
= TS_CMD_HALT
},
3433 { .name
= "arp_waitstate", .value
= TS_CMD_WAITSTATE
},
3434 { .name
= "invoke-event", .value
= TS_CMD_INVOKE_EVENT
},
3436 { .name
= NULL
, .value
= -1 },
3440 /* go past the "command" */
3441 Jim_GetOpt_Setup( &goi
, interp
, argc
-1, argv
+1 );
3443 target
= Jim_CmdPrivData( goi
.interp
);
3444 cmd_ctx
= Jim_GetAssocData(goi
.interp
, "context");
3446 /* commands here are in an NVP table */
3447 e
= Jim_GetOpt_Nvp( &goi
, target_options
, &n
);
3449 Jim_GetOpt_NvpUnknown( &goi
, target_options
, 0 );
3452 // Assume blank result
3453 Jim_SetEmptyResult( goi
.interp
);
3456 case TS_CMD_CONFIGURE
:
3458 Jim_WrongNumArgs( goi
.interp
, goi
.argc
, goi
.argv
, "missing: -option VALUE ...");
3461 goi
.isconfigure
= 1;
3462 return target_configure( &goi
, target
);
3464 // some things take params
3466 Jim_WrongNumArgs( goi
.interp
, 0, goi
.argv
, "missing: ?-option?");
3469 goi
.isconfigure
= 0;
3470 return target_configure( &goi
, target
);
3478 * argv[3] = optional count.
3481 if( (goi
.argc
== 3) || (goi
.argc
== 4) ){
3485 Jim_SetResult_sprintf( goi
.interp
, "expected: %s ADDR DATA [COUNT]", n
->name
);
3489 e
= Jim_GetOpt_Wide( &goi
, &a
);
3494 e
= Jim_GetOpt_Wide( &goi
, &b
);
3499 e
= Jim_GetOpt_Wide( &goi
, &c
);
3509 target_buffer_set_u32( target
, target_buf
, b
);
3513 target_buffer_set_u16( target
, target_buf
, b
);
3517 target_buffer_set_u8( target
, target_buf
, b
);
3521 for( x
= 0 ; x
< c
; x
++ ){
3522 e
= target
->type
->write_memory( target
, a
, b
, 1, target_buf
);
3523 if( e
!= ERROR_OK
){
3524 Jim_SetResult_sprintf( interp
, "Error writing @ 0x%08x: %d\n", (int)(a
), e
);
3537 /* argv[0] = command
3539 * argv[2] = optional count
3541 if( (goi
.argc
== 2) || (goi
.argc
== 3) ){
3542 Jim_SetResult_sprintf( goi
.interp
, "expected: %s ADDR [COUNT]", n
->name
);
3545 e
= Jim_GetOpt_Wide( &goi
, &a
);
3550 e
= Jim_GetOpt_Wide( &goi
, &c
);
3557 b
= 1; /* shut up gcc */
3570 /* convert to "bytes" */
3572 /* count is now in 'BYTES' */
3578 e
= target
->type
->read_memory( target
, a
, b
, y
/ b
, target_buf
);
3579 if( e
!= ERROR_OK
){
3580 Jim_SetResult_sprintf( interp
, "error reading target @ 0x%08lx", (int)(a
) );
3584 Jim_fprintf( interp
, interp
->cookie_stdout
, "0x%08x ", (int)(a
) );
3587 for( x
= 0 ; (x
< 16) && (x
< y
) ; x
+= 4 ){
3588 z
= target_buffer_get_u32( target
, &(target_buf
[ x
* 4 ]) );
3589 Jim_fprintf( interp
, interp
->cookie_stdout
, "%08x ", (int)(z
) );
3591 for( ; (x
< 16) ; x
+= 4 ){
3592 Jim_fprintf( interp
, interp
->cookie_stdout
, " " );
3596 for( x
= 0 ; (x
< 16) && (x
< y
) ; x
+= 2 ){
3597 z
= target_buffer_get_u16( target
, &(target_buf
[ x
* 2 ]) );
3598 Jim_fprintf( interp
, interp
->cookie_stdout
, "%04x ", (int)(z
) );
3600 for( ; (x
< 16) ; x
+= 2 ){
3601 Jim_fprintf( interp
, interp
->cookie_stdout
, " " );
3606 for( x
= 0 ; (x
< 16) && (x
< y
) ; x
+= 1 ){
3607 z
= target_buffer_get_u8( target
, &(target_buf
[ x
* 4 ]) );
3608 Jim_fprintf( interp
, interp
->cookie_stdout
, "%02x ", (int)(z
) );
3610 for( ; (x
< 16) ; x
+= 1 ){
3611 Jim_fprintf( interp
, interp
->cookie_stdout
, " " );
3615 /* ascii-ify the bytes */
3616 for( x
= 0 ; x
< y
; x
++ ){
3617 if( (target_buf
[x
] >= 0x20) &&
3618 (target_buf
[x
] <= 0x7e) ){
3622 target_buf
[x
] = '.';
3627 target_buf
[x
] = ' ';
3632 /* print - with a newline */
3633 Jim_fprintf( interp
, interp
->cookie_stdout
, "%s\n", target_buf
);
3639 case TS_CMD_MEM2ARRAY
:
3640 return target_mem2array( goi
.interp
, target
, goi
.argc
, goi
.argv
);
3642 case TS_CMD_ARRAY2MEM
:
3643 return target_array2mem( goi
.interp
, target
, goi
.argc
, goi
.argv
);
3645 case TS_CMD_EXAMINE
:
3647 Jim_WrongNumArgs( goi
.interp
, 2, argv
, "[no parameters]");
3650 e
= target
->type
->examine( target
);
3651 if( e
!= ERROR_OK
){
3652 Jim_SetResult_sprintf( interp
, "examine-fails: %d", e
);
3658 Jim_WrongNumArgs( goi
.interp
, 2, argv
, "[no parameters]");
3661 if( !(target
->type
->examined
) ){
3662 e
= ERROR_TARGET_NOT_EXAMINED
;
3664 e
= target
->type
->poll( target
);
3666 if( e
!= ERROR_OK
){
3667 Jim_SetResult_sprintf( interp
, "poll-fails: %d", e
);
3674 if( goi
.argc
!= 2 ){
3675 Jim_WrongNumArgs( interp
, 2, argv
, "t|f|assert|deassert BOOL");
3678 e
= Jim_GetOpt_Nvp( &goi
, nvp_assert
, &n
);
3680 Jim_GetOpt_NvpUnknown( &goi
, nvp_assert
, 1 );
3683 // the halt or not param
3684 e
= Jim_GetOpt_Wide( &goi
, &a
);
3688 // determine if we should halt or not.
3689 target
->reset_halt
= !!a
;
3690 // When this happens - all workareas are invalid.
3691 target_free_all_working_areas_restore(target
, 0);
3694 if( n
->value
== NVP_ASSERT
){
3695 target
->type
->assert_reset( target
);
3697 target
->type
->deassert_reset( target
);
3702 Jim_WrongNumArgs( goi
.interp
, 0, argv
, "halt [no parameters]");
3705 target
->type
->halt( target
);
3707 case TS_CMD_WAITSTATE
:
3708 // params: <name> statename timeoutmsecs
3709 if( goi
.argc
!= 2 ){
3710 Jim_SetResult_sprintf( goi
.interp
, "%s STATENAME TIMEOUTMSECS", n
->name
);
3713 e
= Jim_GetOpt_Nvp( &goi
, nvp_target_state
, &n
);
3715 Jim_GetOpt_NvpUnknown( &goi
, nvp_target_state
,1 );
3718 e
= Jim_GetOpt_Wide( &goi
, &a
);
3722 e
= target_wait_state( target
, n
->value
, a
);
3723 if( e
!= ERROR_OK
){
3724 Jim_SetResult_sprintf( goi
.interp
,
3725 "target: %s wait %s fails (%d) %s",
3728 e
, target_strerror_safe(e
) );
3733 case TS_CMD_EVENTLIST
:
3734 /* List for human, Events defined for this target.
3735 * scripts/programs should use 'name cget -event NAME'
3738 target_event_action_t
*teap
;
3739 teap
= target
->event_action
;
3740 command_print( cmd_ctx
, "Event actions for target (%d) %s\n",
3741 target
->target_number
,
3743 command_print( cmd_ctx
, "%-25s | Body", "Event");
3744 command_print( cmd_ctx
, "------------------------- | ----------------------------------------");
3746 command_print( cmd_ctx
,
3748 Jim_Nvp_value2name_simple( nvp_target_event
, teap
->event
)->name
,
3749 Jim_GetString( teap
->body
, NULL
) );
3752 command_print( cmd_ctx
, "***END***");
3755 case TS_CMD_CURSTATE
:
3756 if( goi
.argc
!= 0 ){
3757 Jim_WrongNumArgs( goi
.interp
, 0, argv
, "[no parameters]");
3760 Jim_SetResultString( goi
.interp
,
3761 Jim_Nvp_value2name_simple(nvp_target_state
,target
->state
)->name
,-1);
3763 case TS_CMD_INVOKE_EVENT
:
3764 if( goi
.argc
!= 1 ){
3765 Jim_SetResult_sprintf( goi
.interp
, "%s ?EVENTNAME?",n
->name
);
3768 e
= Jim_GetOpt_Nvp( &goi
, nvp_target_event
, &n
);
3770 Jim_GetOpt_NvpUnknown( &goi
, nvp_target_event
, 1 );
3773 target_handle_event( target
, n
->value
);
3781 target_create( Jim_GetOptInfo
*goi
)
3791 struct command_context_s
*cmd_ctx
;
3793 cmd_ctx
= Jim_GetAssocData(goi
->interp
, "context");
3794 if( goi
->argc
< 3 ){
3795 Jim_WrongNumArgs( goi
->interp
, 1, goi
->argv
, "?name? ?type? ..options...");
3800 Jim_GetOpt_Obj( goi
, &new_cmd
);
3801 /* does this command exist? */
3802 cmd
= Jim_GetCommand( goi
->interp
, new_cmd
, JIM_ERRMSG
);
3804 cp
= Jim_GetString( new_cmd
, NULL
);
3805 Jim_SetResult_sprintf(goi
->interp
, "Command/target: %s Exists", cp
);
3810 e
= Jim_GetOpt_String( goi
, &cp2
, NULL
);
3812 /* now does target type exist */
3813 for( x
= 0 ; target_types
[x
] ; x
++ ){
3814 if( 0 == strcmp( cp
, target_types
[x
]->name
) ){
3819 if( target_types
[x
] == NULL
){
3820 Jim_SetResult_sprintf( goi
->interp
, "Unknown target type %s, try one of ", cp
);
3821 for( x
= 0 ; target_types
[x
] ; x
++ ){
3822 if( target_types
[x
+1] ){
3823 Jim_AppendStrings( goi
->interp
,
3824 Jim_GetResult(goi
->interp
),
3825 target_types
[x
]->name
,
3828 Jim_AppendStrings( goi
->interp
,
3829 Jim_GetResult(goi
->interp
),
3831 target_types
[x
]->name
,NULL
);
3839 target
= calloc(1,sizeof(target_t
));
3840 /* set target number */
3841 target
->target_number
= new_target_number();
3843 /* allocate memory for each unique target type */
3844 target
->type
= (target_type_t
*)calloc(1,sizeof(target_type_t
));
3846 memcpy( target
->type
, target_types
[x
], sizeof(target_type_t
));
3848 /* will be set by "-endian" */
3849 target
->endianness
= TARGET_ENDIAN_UNKNOWN
;
3851 target
->working_area
= 0x0;
3852 target
->working_area_size
= 0x0;
3853 target
->working_areas
= NULL
;
3854 target
->backup_working_area
= 0;
3856 target
->state
= TARGET_UNKNOWN
;
3857 target
->debug_reason
= DBG_REASON_UNDEFINED
;
3858 target
->reg_cache
= NULL
;
3859 target
->breakpoints
= NULL
;
3860 target
->watchpoints
= NULL
;
3861 target
->next
= NULL
;
3862 target
->arch_info
= NULL
;
3864 target
->display
= 1;
3866 /* initialize trace information */
3867 target
->trace_info
= malloc(sizeof(trace_t
));
3868 target
->trace_info
->num_trace_points
= 0;
3869 target
->trace_info
->trace_points_size
= 0;
3870 target
->trace_info
->trace_points
= NULL
;
3871 target
->trace_info
->trace_history_size
= 0;
3872 target
->trace_info
->trace_history
= NULL
;
3873 target
->trace_info
->trace_history_pos
= 0;
3874 target
->trace_info
->trace_history_overflowed
= 0;
3876 target
->dbgmsg
= NULL
;
3877 target
->dbg_msg_enabled
= 0;
3879 target
->endianness
= TARGET_ENDIAN_UNKNOWN
;
3881 /* Do the rest as "configure" options */
3882 goi
->isconfigure
= 1;
3883 e
= target_configure( goi
, target
);
3885 free( target
->type
);
3890 if( target
->endianness
== TARGET_ENDIAN_UNKNOWN
){
3891 /* default endian to little if not specified */
3892 target
->endianness
= TARGET_LITTLE_ENDIAN
;
3895 /* create the target specific commands */
3896 if( target
->type
->register_commands
){
3897 (*(target
->type
->register_commands
))( cmd_ctx
);
3899 if( target
->type
->target_create
){
3900 (*(target
->type
->target_create
))( target
, goi
->interp
);
3903 /* append to end of list */
3906 tpp
= &(all_targets
);
3908 tpp
= &( (*tpp
)->next
);
3913 cp
= Jim_GetString( new_cmd
, NULL
);
3914 target
->cmd_name
= strdup(cp
);
3916 /* now - create the new target name command */
3917 e
= Jim_CreateCommand( goi
->interp
,
3920 tcl_target_func
, /* C function */
3921 target
, /* private data */
3922 NULL
); /* no del proc */
3928 jim_target( Jim_Interp
*interp
, int argc
, Jim_Obj
*const *argv
)
3932 struct command_context_s
*cmd_ctx
;
3936 /* TG = target generic */
3944 const char *target_cmds
[] = {
3945 "create", "types", "names", "current", "number",
3950 LOG_DEBUG("Target command params:");
3951 LOG_DEBUG(Jim_Debug_ArgvString( interp
, argc
, argv
) );
3953 cmd_ctx
= Jim_GetAssocData( interp
, "context" );
3955 Jim_GetOpt_Setup( &goi
, interp
, argc
-1, argv
+1 );
3957 if( goi
.argc
== 0 ){
3958 Jim_WrongNumArgs(interp
, 1, argv
, "missing: command ...");
3962 //Jim_GetOpt_Debug( &goi );
3963 r
= Jim_GetOpt_Enum( &goi
, target_cmds
, &x
);
3970 Jim_Panic(goi
.interp
,"Why am I here?");
3972 case TG_CMD_CURRENT
:
3973 if( goi
.argc
!= 0 ){
3974 Jim_WrongNumArgs( goi
.interp
, 1, goi
.argv
, "Too many parameters");
3977 Jim_SetResultString( goi
.interp
, get_current_target( cmd_ctx
)->cmd_name
, -1 );
3980 if( goi
.argc
!= 0 ){
3981 Jim_WrongNumArgs( goi
.interp
, 1, goi
.argv
, "Too many parameters" );
3984 Jim_SetResult( goi
.interp
, Jim_NewListObj( goi
.interp
, NULL
, 0 ) );
3985 for( x
= 0 ; target_types
[x
] ; x
++ ){
3986 Jim_ListAppendElement( goi
.interp
,
3987 Jim_GetResult(goi
.interp
),
3988 Jim_NewStringObj( goi
.interp
, target_types
[x
]->name
, -1 ) );
3992 if( goi
.argc
!= 0 ){
3993 Jim_WrongNumArgs( goi
.interp
, 1, goi
.argv
, "Too many parameters" );
3996 Jim_SetResult( goi
.interp
, Jim_NewListObj( goi
.interp
, NULL
, 0 ) );
3997 target
= all_targets
;
3999 Jim_ListAppendElement( goi
.interp
,
4000 Jim_GetResult(goi
.interp
),
4001 Jim_NewStringObj( goi
.interp
, target
->cmd_name
, -1 ) );
4002 target
= target
->next
;
4007 Jim_WrongNumArgs( goi
.interp
, goi
.argc
, goi
.argv
, "?name ... config options ...");
4010 return target_create( &goi
);
4013 if( goi
.argc
!= 1 ){
4014 Jim_SetResult_sprintf( goi
.interp
, "expected: target number ?NUMBER?");
4017 e
= Jim_GetOpt_Wide( &goi
, &w
);
4023 t
= get_target_by_num(w
);
4025 Jim_SetResult_sprintf( goi
.interp
,"Target: number %d does not exist", (int)(w
));
4028 Jim_SetResultString( goi
.interp
, t
->cmd_name
, -1 );
4032 if( goi
.argc
!= 0 ){
4033 Jim_WrongNumArgs( goi
.interp
, 0, goi
.argv
, "<no parameters>");
4036 Jim_SetResult( goi
.interp
,
4037 Jim_NewIntObj( goi
.interp
, max_target_number()));
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)