GDB alive fixes for verify_image
[openocd.git] / src / target / target.c
1 /***************************************************************************
2 * Copyright (C) 2005 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
4 * *
5 * Copyright (C) 2007,2008 Øyvind Harboe *
6 * oyvind.harboe@zylin.com *
7 * *
8 * Copyright (C) 2008, Duane Ellis *
9 * openocd@duaneeellis.com *
10 * *
11 * Copyright (C) 2008 by Spencer Oliver *
12 * spen@spen-soft.co.uk *
13 * *
14 * This program is free software; you can redistribute it and/or modify *
15 * it under the terms of the GNU General Public License as published by *
16 * the Free Software Foundation; either version 2 of the License, or *
17 * (at your option) any later version. *
18 * *
19 * This program is distributed in the hope that it will be useful, *
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
22 * GNU General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU General Public License *
25 * along with this program; if not, write to the *
26 * Free Software Foundation, Inc., *
27 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
28 ***************************************************************************/
29 #ifdef HAVE_CONFIG_H
30 #include "config.h"
31 #endif
32
33 #include "replacements.h"
34 #include "target.h"
35 #include "target_request.h"
36
37 #include "log.h"
38 #include "configuration.h"
39 #include "binarybuffer.h"
40 #include "jtag.h"
41
42 #include <string.h>
43 #include <stdlib.h>
44 #include <inttypes.h>
45
46 #include <sys/types.h>
47 #include <sys/stat.h>
48 #include <unistd.h>
49 #include <errno.h>
50
51 #include <sys/time.h>
52 #include <time.h>
53
54 #include <time_support.h>
55
56 #include <fileio.h>
57 #include <image.h>
58
59 static int USE_OLD_RESET = 0; // temp
60
61 int cli_target_callback_event_handler(struct target_s *target, enum target_event event, void *priv);
62
63
64 int handle_targets_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
65
66 int handle_working_area_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
67
68 int handle_reg_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
69 int handle_poll_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
70 int handle_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
71 int handle_wait_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
72 int handle_NEWreset_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
73 int handle_reset_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
74 int handle_soft_reset_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
75 int handle_resume_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
76 int handle_step_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
77 int handle_md_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
78 int handle_mw_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
79 int handle_load_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
80 int handle_dump_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
81 int handle_verify_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
82 int handle_bp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
83 int handle_rbp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
84 int handle_wp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
85 int handle_rwp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
86 int handle_virt2phys_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc);
87 int handle_profile_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
88 static int jim_array2mem(Jim_Interp *interp, int argc, Jim_Obj *const *argv);
89 static int jim_mem2array(Jim_Interp *interp, int argc, Jim_Obj *const *argv);
90 static int jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv);
91
92 static int target_array2mem(Jim_Interp *interp, target_t *target, int argc, Jim_Obj *const *argv);
93 static int target_mem2array(Jim_Interp *interp, target_t *target, int argc, Jim_Obj *const *argv);
94
95
96
97 /* targets */
98 extern target_type_t arm7tdmi_target;
99 extern target_type_t arm720t_target;
100 extern target_type_t arm9tdmi_target;
101 extern target_type_t arm920t_target;
102 extern target_type_t arm966e_target;
103 extern target_type_t arm926ejs_target;
104 extern target_type_t feroceon_target;
105 extern target_type_t xscale_target;
106 extern target_type_t cortexm3_target;
107 extern target_type_t arm11_target;
108 extern target_type_t mips_m4k_target;
109
110 target_type_t *target_types[] =
111 {
112 &arm7tdmi_target,
113 &arm9tdmi_target,
114 &arm920t_target,
115 &arm720t_target,
116 &arm966e_target,
117 &arm926ejs_target,
118 &feroceon_target,
119 &xscale_target,
120 &cortexm3_target,
121 &arm11_target,
122 &mips_m4k_target,
123 NULL,
124 };
125
126 target_t *all_targets = NULL;
127 target_event_callback_t *target_event_callbacks = NULL;
128 target_timer_callback_t *target_timer_callbacks = NULL;
129
130 const Jim_Nvp nvp_assert[] = {
131 { .name = "assert", NVP_ASSERT },
132 { .name = "deassert", NVP_DEASSERT },
133 { .name = "T", NVP_ASSERT },
134 { .name = "F", NVP_DEASSERT },
135 { .name = "t", NVP_ASSERT },
136 { .name = "f", NVP_DEASSERT },
137 { .name = NULL, .value = -1 }
138 };
139
140 const Jim_Nvp nvp_error_target[] = {
141 { .value = ERROR_TARGET_INVALID, .name = "err-invalid" },
142 { .value = ERROR_TARGET_INIT_FAILED, .name = "err-init-failed" },
143 { .value = ERROR_TARGET_TIMEOUT, .name = "err-timeout" },
144 { .value = ERROR_TARGET_NOT_HALTED, .name = "err-not-halted" },
145 { .value = ERROR_TARGET_FAILURE, .name = "err-failure" },
146 { .value = ERROR_TARGET_UNALIGNED_ACCESS , .name = "err-unaligned-access" },
147 { .value = ERROR_TARGET_DATA_ABORT , .name = "err-data-abort" },
148 { .value = ERROR_TARGET_RESOURCE_NOT_AVAILABLE , .name = "err-resource-not-available" },
149 { .value = ERROR_TARGET_TRANSLATION_FAULT , .name = "err-translation-fault" },
150 { .value = ERROR_TARGET_NOT_RUNNING, .name = "err-not-running" },
151 { .value = ERROR_TARGET_NOT_EXAMINED, .name = "err-not-examined" },
152 { .value = -1, .name = NULL }
153 };
154
155 const char *target_strerror_safe( int err )
156 {
157 const Jim_Nvp *n;
158
159 n = Jim_Nvp_value2name_simple( nvp_error_target, err );
160 if( n->name == NULL ){
161 return "unknown";
162 } else {
163 return n->name;
164 }
165 }
166
167 const Jim_Nvp nvp_target_event[] = {
168 { .value = TARGET_EVENT_OLD_pre_reset , .name = "old-pre_reset" },
169 { .value = TARGET_EVENT_OLD_gdb_program_config , .name = "old-gdb_program_config" },
170 { .value = TARGET_EVENT_OLD_post_reset , .name = "old-post_reset" },
171 { .value = TARGET_EVENT_OLD_pre_resume , .name = "old-pre_resume" },
172
173
174 { .value = TARGET_EVENT_EARLY_HALTED, .name = "early-halted" },
175 { .value = TARGET_EVENT_HALTED, .name = "halted" },
176 { .value = TARGET_EVENT_RESUMED, .name = "resumed" },
177 { .value = TARGET_EVENT_RESUME_START, .name = "resume-start" },
178 { .value = TARGET_EVENT_RESUME_END, .name = "resume-end" },
179
180 /* historical name */
181
182 { .value = TARGET_EVENT_RESET_START, .name = "reset-start" },
183
184 { .value = TARGET_EVENT_RESET_ASSERT_PRE, .name = "reset-assert-pre" },
185 { .value = TARGET_EVENT_RESET_ASSERT_POST, .name = "reset-assert-post" },
186 { .value = TARGET_EVENT_RESET_DEASSERT_PRE, .name = "reset-deassert-pre" },
187 { .value = TARGET_EVENT_RESET_DEASSERT_POST, .name = "reset-deassert-post" },
188 { .value = TARGET_EVENT_RESET_HALT_PRE, .name = "reset-halt-pre" },
189 { .value = TARGET_EVENT_RESET_HALT_POST, .name = "reset-halt-post" },
190 { .value = TARGET_EVENT_RESET_WAIT_PRE, .name = "reset-wait-pre" },
191 { .value = TARGET_EVENT_RESET_WAIT_POST, .name = "reset-wait-post" },
192 { .value = TARGET_EVENT_RESET_INIT , .name = "reset-init" },
193 { .value = TARGET_EVENT_RESET_END, .name = "reset-end" },
194
195
196
197
198
199 { .value = TARGET_EVENT_EXAMINE_START, .name = "examine-start" },
200 { .value = TARGET_EVENT_EXAMINE_START, .name = "examine-end" },
201
202
203 { .value = TARGET_EVENT_DEBUG_HALTED, .name = "debug-halted" },
204 { .value = TARGET_EVENT_DEBUG_RESUMED, .name = "debug-resumed" },
205
206 { .value = TARGET_EVENT_GDB_ATTACH, .name = "gdb-attach" },
207 { .value = TARGET_EVENT_GDB_DETACH, .name = "gdb-detach" },
208
209
210 { .value = TARGET_EVENT_GDB_FLASH_WRITE_START, .name = "gdb-flash-write-start" },
211 { .value = TARGET_EVENT_GDB_FLASH_WRITE_END , .name = "gdb-flash-write-end" },
212
213 { .value = TARGET_EVENT_GDB_FLASH_ERASE_START, .name = "gdb-flash-erase-start" },
214 { .value = TARGET_EVENT_GDB_FLASH_ERASE_END , .name = "gdb-flash-erase-end" },
215
216 { .value = TARGET_EVENT_RESUME_START, .name = "resume-start" },
217 { .value = TARGET_EVENT_RESUMED , .name = "resume-ok" },
218 { .value = TARGET_EVENT_RESUME_END , .name = "resume-end" },
219
220 { .name = NULL, .value = -1 }
221 };
222
223 const Jim_Nvp nvp_target_state[] = {
224 { .name = "unknown", .value = TARGET_UNKNOWN },
225 { .name = "running", .value = TARGET_RUNNING },
226 { .name = "halted", .value = TARGET_HALTED },
227 { .name = "reset", .value = TARGET_RESET },
228 { .name = "debug-running", .value = TARGET_DEBUG_RUNNING },
229 { .name = NULL, .value = -1 },
230 };
231
232
233 const Jim_Nvp nvp_target_debug_reason [] = {
234 { .name = "debug-request" , .value = DBG_REASON_DBGRQ },
235 { .name = "breakpoint" , .value = DBG_REASON_BREAKPOINT },
236 { .name = "watchpoint" , .value = DBG_REASON_WATCHPOINT },
237 { .name = "watchpoint-and-breakpoint", .value = DBG_REASON_WPTANDBKPT },
238 { .name = "single-step" , .value = DBG_REASON_SINGLESTEP },
239 { .name = "target-not-halted" , .value = DBG_REASON_NOTHALTED },
240 { .name = "undefined" , .value = DBG_REASON_UNDEFINED },
241 { .name = NULL, .value = -1 },
242 };
243
244
245 const Jim_Nvp nvp_target_endian[] = {
246 { .name = "big", .value = TARGET_BIG_ENDIAN },
247 { .name = "little", .value = TARGET_LITTLE_ENDIAN },
248 { .name = "be", .value = TARGET_BIG_ENDIAN },
249 { .name = "le", .value = TARGET_LITTLE_ENDIAN },
250 { .name = NULL, .value = -1 },
251 };
252
253 const Jim_Nvp nvp_reset_modes[] = {
254 { .name = "unknown", .value = RESET_UNKNOWN },
255 { .name = "run" , .value = RESET_RUN },
256 { .name = "halt" , .value = RESET_HALT },
257 { .name = "init" , .value = RESET_INIT },
258 { .name = NULL , .value = -1 },
259 };
260
261 static int
262 max_target_number( void )
263 {
264 target_t *t;
265 int x;
266
267 x = -1;
268 t = all_targets;
269 while( t ){
270 if( x < t->target_number ){
271 x = (t->target_number)+1;
272 }
273 t = t->next;
274 }
275 return x;
276 }
277
278 /* determine the number of the new target */
279 static int
280 new_target_number( void )
281 {
282 target_t *t;
283 int x;
284
285 /* number is 0 based */
286 x = -1;
287 t = all_targets;
288 while(t){
289 if( x < t->target_number ){
290 x = t->target_number;
291 }
292 t = t->next;
293 }
294 return x+1;
295 }
296
297 static int target_continous_poll = 1;
298
299 /* read a u32 from a buffer in target memory endianness */
300 u32 target_buffer_get_u32(target_t *target, u8 *buffer)
301 {
302 if (target->endianness == TARGET_LITTLE_ENDIAN)
303 return le_to_h_u32(buffer);
304 else
305 return be_to_h_u32(buffer);
306 }
307
308 /* read a u16 from a buffer in target memory endianness */
309 u16 target_buffer_get_u16(target_t *target, u8 *buffer)
310 {
311 if (target->endianness == TARGET_LITTLE_ENDIAN)
312 return le_to_h_u16(buffer);
313 else
314 return be_to_h_u16(buffer);
315 }
316
317 /* read a u8 from a buffer in target memory endianness */
318 u8 target_buffer_get_u8(target_t *target, u8 *buffer)
319 {
320 return *buffer & 0x0ff;
321 }
322
323 /* write a u32 to a buffer in target memory endianness */
324 void target_buffer_set_u32(target_t *target, u8 *buffer, u32 value)
325 {
326 if (target->endianness == TARGET_LITTLE_ENDIAN)
327 h_u32_to_le(buffer, value);
328 else
329 h_u32_to_be(buffer, value);
330 }
331
332 /* write a u16 to a buffer in target memory endianness */
333 void target_buffer_set_u16(target_t *target, u8 *buffer, u16 value)
334 {
335 if (target->endianness == TARGET_LITTLE_ENDIAN)
336 h_u16_to_le(buffer, value);
337 else
338 h_u16_to_be(buffer, value);
339 }
340
341 /* write a u8 to a buffer in target memory endianness */
342 void target_buffer_set_u8(target_t *target, u8 *buffer, u8 value)
343 {
344 *buffer = value;
345 }
346
347 /* returns a pointer to the n-th configured target */
348 target_t* get_target_by_num(int num)
349 {
350 target_t *target = all_targets;
351
352 while (target){
353 if( target->target_number == num ){
354 return target;
355 }
356 target = target->next;
357 }
358
359 return NULL;
360 }
361
362 int get_num_by_target(target_t *query_target)
363 {
364 return query_target->target_number;
365 }
366
367 target_t* get_current_target(command_context_t *cmd_ctx)
368 {
369 target_t *target = get_target_by_num(cmd_ctx->current_target);
370
371 if (target == NULL)
372 {
373 LOG_ERROR("BUG: current_target out of bounds");
374 exit(-1);
375 }
376
377 return target;
378 }
379
380
381 int target_poll(struct target_s *target)
382 {
383 /* We can't poll until after examine */
384 if (!target->type->examined)
385 {
386 /* Fail silently lest we pollute the log */
387 return ERROR_FAIL;
388 }
389 return target->type->poll(target);
390 }
391
392 int target_halt(struct target_s *target)
393 {
394 /* We can't poll until after examine */
395 if (!target->type->examined)
396 {
397 LOG_ERROR("Target not examined yet");
398 return ERROR_FAIL;
399 }
400 return target->type->halt(target);
401 }
402
403 int target_resume(struct target_s *target, int current, u32 address, int handle_breakpoints, int debug_execution)
404 {
405 int retval;
406
407 /* We can't poll until after examine */
408 if (!target->type->examined)
409 {
410 LOG_ERROR("Target not examined yet");
411 return ERROR_FAIL;
412 }
413
414 /* note that resume *must* be asynchronous. The CPU can halt before we poll. The CPU can
415 * even halt at the current PC as a result of a software breakpoint being inserted by (a bug?)
416 * the application.
417 */
418 if ((retval = target->type->resume(target, current, address, handle_breakpoints, debug_execution)) != ERROR_OK)
419 return retval;
420
421 return retval;
422 }
423
424
425 static int NEW_target_process_reset(struct command_context_s *cmd_ctx, enum target_reset_mode reset_mode)
426 {
427 char buf[100];
428 Jim_Nvp *n;
429 n = Jim_Nvp_value2name_simple( nvp_reset_modes, reset_mode );
430 if( n->name == NULL ){
431 LOG_ERROR("invalid reset mode");
432 return ERROR_FAIL;
433 }
434
435 sprintf( buf, "ocd_process_reset %s", n->name );
436 Jim_Eval( interp, buf );
437
438 /* We want any events to be processed before the prompt */
439 target_call_timer_callbacks_now();
440
441 return ERROR_OK;
442 }
443
444 // Next patch - this turns into TCL...
445 static int OLD_target_process_reset(struct command_context_s *cmd_ctx, enum target_reset_mode reset_mode)
446 {
447 int retval = ERROR_OK;
448 target_t *target;
449
450 target = all_targets;
451
452 target_all_handle_event( TARGET_EVENT_OLD_pre_reset );
453
454 if ((retval = jtag_init_reset(cmd_ctx)) != ERROR_OK)
455 return retval;
456
457 keep_alive(); /* we might be running on a very slow JTAG clk */
458
459 /* First time this is executed after launching OpenOCD, it will read out
460 * the type of CPU, etc. and init Embedded ICE registers in host
461 * memory.
462 *
463 * It will also set up ICE registers in the target.
464 *
465 * However, if we assert TRST later, we need to set up the registers again.
466 *
467 * For the "reset halt/init" case we must only set up the registers here.
468 */
469 if ((retval = target_examine()) != ERROR_OK)
470 return retval;
471
472 keep_alive(); /* we might be running on a very slow JTAG clk */
473
474 target = all_targets;
475 while (target)
476 {
477 /* we have no idea what state the target is in, so we
478 * have to drop working areas
479 */
480 target_free_all_working_areas_restore(target, 0);
481 target->reset_halt=((reset_mode==RESET_HALT)||(reset_mode==RESET_INIT));
482 if ((retval = target->type->assert_reset(target))!=ERROR_OK)
483 return retval;
484 target = target->next;
485 }
486
487 target = all_targets;
488 while (target)
489 {
490 if ((retval = target->type->deassert_reset(target))!=ERROR_OK)
491 return retval;
492 target = target->next;
493 }
494
495 target = all_targets;
496 while (target)
497 {
498 /* We can fail to bring the target into the halted state, try after reset has been deasserted */
499 if (target->reset_halt)
500 {
501 /* wait up to 1 second for halt. */
502 target_wait_state(target, TARGET_HALTED, 1000);
503 if (target->state != TARGET_HALTED)
504 {
505 LOG_WARNING("Failed to reset target into halted mode - issuing halt");
506 if ((retval = target->type->halt(target))!=ERROR_OK)
507 return retval;
508 }
509 }
510
511 target = target->next;
512 }
513
514
515 LOG_DEBUG("Waiting for halted stated as appropriate");
516
517 if ((reset_mode == RESET_HALT) || (reset_mode == RESET_INIT))
518 {
519 target = all_targets;
520 while (target)
521 {
522 /* Wait for reset to complete, maximum 5 seconds. */
523 if (((retval=target_wait_state(target, TARGET_HALTED, 5000)))==ERROR_OK)
524 {
525 if (reset_mode == RESET_INIT){
526 target_handle_event( target, TARGET_EVENT_OLD_post_reset );
527 }
528
529 }
530 target = target->next;
531 }
532 }
533
534 /* We want any events to be processed before the prompt */
535 target_call_timer_callbacks_now();
536
537 return retval;
538 }
539
540 int target_process_reset(struct command_context_s *cmd_ctx, enum target_reset_mode reset_mode)
541 {
542 if( USE_OLD_RESET ){
543 return OLD_target_process_reset( cmd_ctx, reset_mode );
544 } else {
545 return NEW_target_process_reset( cmd_ctx, reset_mode );
546 }
547 }
548
549
550 static int default_virt2phys(struct target_s *target, u32 virtual, u32 *physical)
551 {
552 *physical = virtual;
553 return ERROR_OK;
554 }
555
556 static int default_mmu(struct target_s *target, int *enabled)
557 {
558 *enabled = 0;
559 return ERROR_OK;
560 }
561
562 static int default_examine(struct target_s *target)
563 {
564 target->type->examined = 1;
565 return ERROR_OK;
566 }
567
568
569 /* Targets that correctly implement init+examine, i.e.
570 * no communication with target during init:
571 *
572 * XScale
573 */
574 int target_examine(void)
575 {
576 int retval = ERROR_OK;
577 target_t *target = all_targets;
578 while (target)
579 {
580 if ((retval = target->type->examine(target))!=ERROR_OK)
581 return retval;
582 target = target->next;
583 }
584 return retval;
585 }
586
587 static int target_write_memory_imp(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer)
588 {
589 if (!target->type->examined)
590 {
591 LOG_ERROR("Target not examined yet");
592 return ERROR_FAIL;
593 }
594 return target->type->write_memory_imp(target, address, size, count, buffer);
595 }
596
597 static int target_read_memory_imp(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer)
598 {
599 if (!target->type->examined)
600 {
601 LOG_ERROR("Target not examined yet");
602 return ERROR_FAIL;
603 }
604 return target->type->read_memory_imp(target, address, size, count, buffer);
605 }
606
607 static int target_soft_reset_halt_imp(struct target_s *target)
608 {
609 if (!target->type->examined)
610 {
611 LOG_ERROR("Target not examined yet");
612 return ERROR_FAIL;
613 }
614 return target->type->soft_reset_halt_imp(target);
615 }
616
617 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)
618 {
619 if (!target->type->examined)
620 {
621 LOG_ERROR("Target not examined yet");
622 return ERROR_FAIL;
623 }
624 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);
625 }
626
627 int target_init(struct command_context_s *cmd_ctx)
628 {
629 target_t *target = all_targets;
630
631 while (target)
632 {
633 target->type->examined = 0;
634 if (target->type->examine == NULL)
635 {
636 target->type->examine = default_examine;
637 }
638
639 if (target->type->init_target(cmd_ctx, target) != ERROR_OK)
640 {
641 LOG_ERROR("target '%s' init failed", target->type->name);
642 exit(-1);
643 }
644
645 /* Set up default functions if none are provided by target */
646 if (target->type->virt2phys == NULL)
647 {
648 target->type->virt2phys = default_virt2phys;
649 }
650 target->type->virt2phys = default_virt2phys;
651 /* a non-invasive way(in terms of patches) to add some code that
652 * runs before the type->write/read_memory implementation
653 */
654 target->type->write_memory_imp = target->type->write_memory;
655 target->type->write_memory = target_write_memory_imp;
656 target->type->read_memory_imp = target->type->read_memory;
657 target->type->read_memory = target_read_memory_imp;
658 target->type->soft_reset_halt_imp = target->type->soft_reset_halt;
659 target->type->soft_reset_halt = target_soft_reset_halt_imp;
660 target->type->run_algorithm_imp = target->type->run_algorithm;
661 target->type->run_algorithm = target_run_algorithm_imp;
662
663
664 if (target->type->mmu == NULL)
665 {
666 target->type->mmu = default_mmu;
667 }
668 target = target->next;
669 }
670
671 if (all_targets)
672 {
673 target_register_user_commands(cmd_ctx);
674 target_register_timer_callback(handle_target, 100, 1, NULL);
675 }
676
677 return ERROR_OK;
678 }
679
680 int target_register_event_callback(int (*callback)(struct target_s *target, enum target_event event, void *priv), void *priv)
681 {
682 target_event_callback_t **callbacks_p = &target_event_callbacks;
683
684 if (callback == NULL)
685 {
686 return ERROR_INVALID_ARGUMENTS;
687 }
688
689 if (*callbacks_p)
690 {
691 while ((*callbacks_p)->next)
692 callbacks_p = &((*callbacks_p)->next);
693 callbacks_p = &((*callbacks_p)->next);
694 }
695
696 (*callbacks_p) = malloc(sizeof(target_event_callback_t));
697 (*callbacks_p)->callback = callback;
698 (*callbacks_p)->priv = priv;
699 (*callbacks_p)->next = NULL;
700
701 return ERROR_OK;
702 }
703
704 int target_register_timer_callback(int (*callback)(void *priv), int time_ms, int periodic, void *priv)
705 {
706 target_timer_callback_t **callbacks_p = &target_timer_callbacks;
707 struct timeval now;
708
709 if (callback == NULL)
710 {
711 return ERROR_INVALID_ARGUMENTS;
712 }
713
714 if (*callbacks_p)
715 {
716 while ((*callbacks_p)->next)
717 callbacks_p = &((*callbacks_p)->next);
718 callbacks_p = &((*callbacks_p)->next);
719 }
720
721 (*callbacks_p) = malloc(sizeof(target_timer_callback_t));
722 (*callbacks_p)->callback = callback;
723 (*callbacks_p)->periodic = periodic;
724 (*callbacks_p)->time_ms = time_ms;
725
726 gettimeofday(&now, NULL);
727 (*callbacks_p)->when.tv_usec = now.tv_usec + (time_ms % 1000) * 1000;
728 time_ms -= (time_ms % 1000);
729 (*callbacks_p)->when.tv_sec = now.tv_sec + (time_ms / 1000);
730 if ((*callbacks_p)->when.tv_usec > 1000000)
731 {
732 (*callbacks_p)->when.tv_usec = (*callbacks_p)->when.tv_usec - 1000000;
733 (*callbacks_p)->when.tv_sec += 1;
734 }
735
736 (*callbacks_p)->priv = priv;
737 (*callbacks_p)->next = NULL;
738
739 return ERROR_OK;
740 }
741
742 int target_unregister_event_callback(int (*callback)(struct target_s *target, enum target_event event, void *priv), void *priv)
743 {
744 target_event_callback_t **p = &target_event_callbacks;
745 target_event_callback_t *c = target_event_callbacks;
746
747 if (callback == NULL)
748 {
749 return ERROR_INVALID_ARGUMENTS;
750 }
751
752 while (c)
753 {
754 target_event_callback_t *next = c->next;
755 if ((c->callback == callback) && (c->priv == priv))
756 {
757 *p = next;
758 free(c);
759 return ERROR_OK;
760 }
761 else
762 p = &(c->next);
763 c = next;
764 }
765
766 return ERROR_OK;
767 }
768
769 int target_unregister_timer_callback(int (*callback)(void *priv), void *priv)
770 {
771 target_timer_callback_t **p = &target_timer_callbacks;
772 target_timer_callback_t *c = target_timer_callbacks;
773
774 if (callback == NULL)
775 {
776 return ERROR_INVALID_ARGUMENTS;
777 }
778
779 while (c)
780 {
781 target_timer_callback_t *next = c->next;
782 if ((c->callback == callback) && (c->priv == priv))
783 {
784 *p = next;
785 free(c);
786 return ERROR_OK;
787 }
788 else
789 p = &(c->next);
790 c = next;
791 }
792
793 return ERROR_OK;
794 }
795
796 int target_call_event_callbacks(target_t *target, enum target_event event)
797 {
798 target_event_callback_t *callback = target_event_callbacks;
799 target_event_callback_t *next_callback;
800
801 if (event == TARGET_EVENT_HALTED)
802 {
803 /* execute early halted first */
804 target_call_event_callbacks(target, TARGET_EVENT_EARLY_HALTED);
805 }
806
807
808 LOG_DEBUG("target event %i (%s)",
809 event,
810 Jim_Nvp_value2name_simple( nvp_target_event, event )->name );
811
812 target_handle_event( target, event );
813
814 while (callback)
815 {
816 next_callback = callback->next;
817 callback->callback(target, event, callback->priv);
818 callback = next_callback;
819 }
820
821 return ERROR_OK;
822 }
823
824 static int target_call_timer_callbacks_check_time(int checktime)
825 {
826 target_timer_callback_t *callback = target_timer_callbacks;
827 target_timer_callback_t *next_callback;
828 struct timeval now;
829
830 keep_alive();
831
832 gettimeofday(&now, NULL);
833
834 while (callback)
835 {
836 next_callback = callback->next;
837
838 if ((!checktime&&callback->periodic)||
839 (((now.tv_sec >= callback->when.tv_sec) && (now.tv_usec >= callback->when.tv_usec))
840 || (now.tv_sec > callback->when.tv_sec)))
841 {
842 if(callback->callback != NULL)
843 {
844 callback->callback(callback->priv);
845 if (callback->periodic)
846 {
847 int time_ms = callback->time_ms;
848 callback->when.tv_usec = now.tv_usec + (time_ms % 1000) * 1000;
849 time_ms -= (time_ms % 1000);
850 callback->when.tv_sec = now.tv_sec + time_ms / 1000;
851 if (callback->when.tv_usec > 1000000)
852 {
853 callback->when.tv_usec = callback->when.tv_usec - 1000000;
854 callback->when.tv_sec += 1;
855 }
856 }
857 else
858 target_unregister_timer_callback(callback->callback, callback->priv);
859 }
860 }
861
862 callback = next_callback;
863 }
864
865 return ERROR_OK;
866 }
867
868 int target_call_timer_callbacks(void)
869 {
870 return target_call_timer_callbacks_check_time(1);
871 }
872
873 /* invoke periodic callbacks immediately */
874 int target_call_timer_callbacks_now(void)
875 {
876 return target_call_timer_callbacks_check_time(0);
877 }
878
879 int target_alloc_working_area(struct target_s *target, u32 size, working_area_t **area)
880 {
881 working_area_t *c = target->working_areas;
882 working_area_t *new_wa = NULL;
883
884 /* Reevaluate working area address based on MMU state*/
885 if (target->working_areas == NULL)
886 {
887 int retval;
888 int enabled;
889 retval = target->type->mmu(target, &enabled);
890 if (retval != ERROR_OK)
891 {
892 return retval;
893 }
894 if (enabled)
895 {
896 target->working_area = target->working_area_virt;
897 }
898 else
899 {
900 target->working_area = target->working_area_phys;
901 }
902 }
903
904 /* only allocate multiples of 4 byte */
905 if (size % 4)
906 {
907 LOG_ERROR("BUG: code tried to allocate unaligned number of bytes, padding");
908 size = CEIL(size, 4);
909 }
910
911 /* see if there's already a matching working area */
912 while (c)
913 {
914 if ((c->free) && (c->size == size))
915 {
916 new_wa = c;
917 break;
918 }
919 c = c->next;
920 }
921
922 /* if not, allocate a new one */
923 if (!new_wa)
924 {
925 working_area_t **p = &target->working_areas;
926 u32 first_free = target->working_area;
927 u32 free_size = target->working_area_size;
928
929 LOG_DEBUG("allocating new working area");
930
931 c = target->working_areas;
932 while (c)
933 {
934 first_free += c->size;
935 free_size -= c->size;
936 p = &c->next;
937 c = c->next;
938 }
939
940 if (free_size < size)
941 {
942 LOG_WARNING("not enough working area available(requested %d, free %d)", size, free_size);
943 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
944 }
945
946 new_wa = malloc(sizeof(working_area_t));
947 new_wa->next = NULL;
948 new_wa->size = size;
949 new_wa->address = first_free;
950
951 if (target->backup_working_area)
952 {
953 new_wa->backup = malloc(new_wa->size);
954 target->type->read_memory(target, new_wa->address, 4, new_wa->size / 4, new_wa->backup);
955 }
956 else
957 {
958 new_wa->backup = NULL;
959 }
960
961 /* put new entry in list */
962 *p = new_wa;
963 }
964
965 /* mark as used, and return the new (reused) area */
966 new_wa->free = 0;
967 *area = new_wa;
968
969 /* user pointer */
970 new_wa->user = area;
971
972 return ERROR_OK;
973 }
974
975 int target_free_working_area_restore(struct target_s *target, working_area_t *area, int restore)
976 {
977 if (area->free)
978 return ERROR_OK;
979
980 if (restore&&target->backup_working_area)
981 target->type->write_memory(target, area->address, 4, area->size / 4, area->backup);
982
983 area->free = 1;
984
985 /* mark user pointer invalid */
986 *area->user = NULL;
987 area->user = NULL;
988
989 return ERROR_OK;
990 }
991
992 int target_free_working_area(struct target_s *target, working_area_t *area)
993 {
994 return target_free_working_area_restore(target, area, 1);
995 }
996
997 int target_free_all_working_areas_restore(struct target_s *target, int restore)
998 {
999 working_area_t *c = target->working_areas;
1000
1001 while (c)
1002 {
1003 working_area_t *next = c->next;
1004 target_free_working_area_restore(target, c, restore);
1005
1006 if (c->backup)
1007 free(c->backup);
1008
1009 free(c);
1010
1011 c = next;
1012 }
1013
1014 target->working_areas = NULL;
1015
1016 return ERROR_OK;
1017 }
1018
1019 int target_free_all_working_areas(struct target_s *target)
1020 {
1021 return target_free_all_working_areas_restore(target, 1);
1022 }
1023
1024 int target_register_commands(struct command_context_s *cmd_ctx)
1025 {
1026
1027 register_command(cmd_ctx, NULL, "targets", handle_targets_command, COMMAND_EXEC, NULL);
1028 register_command(cmd_ctx, NULL, "working_area", handle_working_area_command, COMMAND_ANY, "working_area <target#> <address> <size> <'backup'|'nobackup'> [virtual address]");
1029 register_command(cmd_ctx, NULL, "virt2phys", handle_virt2phys_command, COMMAND_ANY, "virt2phys <virtual address>");
1030 register_command(cmd_ctx, NULL, "profile", handle_profile_command, COMMAND_EXEC, "PRELIMINARY! - profile <seconds> <gmon.out>");
1031
1032 register_jim(cmd_ctx, "target", jim_target, "configure target" );
1033
1034
1035 /* script procedures */
1036 register_jim(cmd_ctx, "ocd_mem2array", jim_mem2array, "read memory and return as a TCL array for script processing");
1037 register_jim(cmd_ctx, "ocd_array2mem", jim_array2mem, "convert a TCL array to memory locations and write the values");
1038 return ERROR_OK;
1039 }
1040
1041 int target_arch_state(struct target_s *target)
1042 {
1043 int retval;
1044 if (target==NULL)
1045 {
1046 LOG_USER("No target has been configured");
1047 return ERROR_OK;
1048 }
1049
1050 LOG_USER("target state: %s",
1051 Jim_Nvp_value2name_simple(nvp_target_state,target->state)->name);
1052
1053 if (target->state!=TARGET_HALTED)
1054 return ERROR_OK;
1055
1056 retval=target->type->arch_state(target);
1057 return retval;
1058 }
1059
1060 /* Single aligned words are guaranteed to use 16 or 32 bit access
1061 * mode respectively, otherwise data is handled as quickly as
1062 * possible
1063 */
1064 int target_write_buffer(struct target_s *target, u32 address, u32 size, u8 *buffer)
1065 {
1066 int retval;
1067 LOG_DEBUG("writing buffer of %i byte at 0x%8.8x", size, address);
1068
1069 if (!target->type->examined)
1070 {
1071 LOG_ERROR("Target not examined yet");
1072 return ERROR_FAIL;
1073 }
1074
1075 if ((address + size - 1) < address)
1076 {
1077 /* GDB can request this when e.g. PC is 0xfffffffc*/
1078 LOG_ERROR("address+size wrapped(0x%08x, 0x%08x)", address, size);
1079 return ERROR_FAIL;
1080 }
1081
1082 if (((address % 2) == 0) && (size == 2))
1083 {
1084 return target->type->write_memory(target, address, 2, 1, buffer);
1085 }
1086
1087 /* handle unaligned head bytes */
1088 if (address % 4)
1089 {
1090 int unaligned = 4 - (address % 4);
1091
1092 if (unaligned > size)
1093 unaligned = size;
1094
1095 if ((retval = target->type->write_memory(target, address, 1, unaligned, buffer)) != ERROR_OK)
1096 return retval;
1097
1098 buffer += unaligned;
1099 address += unaligned;
1100 size -= unaligned;
1101 }
1102
1103 /* handle aligned words */
1104 if (size >= 4)
1105 {
1106 int aligned = size - (size % 4);
1107
1108 /* use bulk writes above a certain limit. This may have to be changed */
1109 if (aligned > 128)
1110 {
1111 if ((retval = target->type->bulk_write_memory(target, address, aligned / 4, buffer)) != ERROR_OK)
1112 return retval;
1113 }
1114 else
1115 {
1116 if ((retval = target->type->write_memory(target, address, 4, aligned / 4, buffer)) != ERROR_OK)
1117 return retval;
1118 }
1119
1120 buffer += aligned;
1121 address += aligned;
1122 size -= aligned;
1123 }
1124
1125 /* handle tail writes of less than 4 bytes */
1126 if (size > 0)
1127 {
1128 if ((retval = target->type->write_memory(target, address, 1, size, buffer)) != ERROR_OK)
1129 return retval;
1130 }
1131
1132 return ERROR_OK;
1133 }
1134
1135
1136 /* Single aligned words are guaranteed to use 16 or 32 bit access
1137 * mode respectively, otherwise data is handled as quickly as
1138 * possible
1139 */
1140 int target_read_buffer(struct target_s *target, u32 address, u32 size, u8 *buffer)
1141 {
1142 int retval;
1143 LOG_DEBUG("reading buffer of %i byte at 0x%8.8x", size, address);
1144
1145 if (!target->type->examined)
1146 {
1147 LOG_ERROR("Target not examined yet");
1148 return ERROR_FAIL;
1149 }
1150
1151 if ((address + size - 1) < address)
1152 {
1153 /* GDB can request this when e.g. PC is 0xfffffffc*/
1154 LOG_ERROR("address+size wrapped(0x%08x, 0x%08x)", address, size);
1155 return ERROR_FAIL;
1156 }
1157
1158 if (((address % 2) == 0) && (size == 2))
1159 {
1160 return target->type->read_memory(target, address, 2, 1, buffer);
1161 }
1162
1163 /* handle unaligned head bytes */
1164 if (address % 4)
1165 {
1166 int unaligned = 4 - (address % 4);
1167
1168 if (unaligned > size)
1169 unaligned = size;
1170
1171 if ((retval = target->type->read_memory(target, address, 1, unaligned, buffer)) != ERROR_OK)
1172 return retval;
1173
1174 buffer += unaligned;
1175 address += unaligned;
1176 size -= unaligned;
1177 }
1178
1179 /* handle aligned words */
1180 if (size >= 4)
1181 {
1182 int aligned = size - (size % 4);
1183
1184 if ((retval = target->type->read_memory(target, address, 4, aligned / 4, buffer)) != ERROR_OK)
1185 return retval;
1186
1187 buffer += aligned;
1188 address += aligned;
1189 size -= aligned;
1190 }
1191
1192 /* handle tail writes of less than 4 bytes */
1193 if (size > 0)
1194 {
1195 if ((retval = target->type->read_memory(target, address, 1, size, buffer)) != ERROR_OK)
1196 return retval;
1197 }
1198
1199 return ERROR_OK;
1200 }
1201
1202 int target_checksum_memory(struct target_s *target, u32 address, u32 size, u32* crc)
1203 {
1204 u8 *buffer;
1205 int retval;
1206 int i;
1207 u32 checksum = 0;
1208 if (!target->type->examined)
1209 {
1210 LOG_ERROR("Target not examined yet");
1211 return ERROR_FAIL;
1212 }
1213
1214 if ((retval = target->type->checksum_memory(target, address,
1215 size, &checksum)) == ERROR_TARGET_RESOURCE_NOT_AVAILABLE)
1216 {
1217 buffer = malloc(size);
1218 if (buffer == NULL)
1219 {
1220 LOG_ERROR("error allocating buffer for section (%d bytes)", size);
1221 return ERROR_INVALID_ARGUMENTS;
1222 }
1223 retval = target_read_buffer(target, address, size, buffer);
1224 if (retval != ERROR_OK)
1225 {
1226 free(buffer);
1227 return retval;
1228 }
1229
1230 /* convert to target endianess */
1231 for (i = 0; i < (size/sizeof(u32)); i++)
1232 {
1233 u32 target_data;
1234 target_data = target_buffer_get_u32(target, &buffer[i*sizeof(u32)]);
1235 target_buffer_set_u32(target, &buffer[i*sizeof(u32)], target_data);
1236 }
1237
1238 retval = image_calculate_checksum( buffer, size, &checksum );
1239 free(buffer);
1240 }
1241
1242 *crc = checksum;
1243
1244 return retval;
1245 }
1246
1247 int target_blank_check_memory(struct target_s *target, u32 address, u32 size, u32* blank)
1248 {
1249 int retval;
1250 if (!target->type->examined)
1251 {
1252 LOG_ERROR("Target not examined yet");
1253 return ERROR_FAIL;
1254 }
1255
1256 if (target->type->blank_check_memory == 0)
1257 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
1258
1259 retval = target->type->blank_check_memory(target, address, size, blank);
1260
1261 return retval;
1262 }
1263
1264 int target_read_u32(struct target_s *target, u32 address, u32 *value)
1265 {
1266 u8 value_buf[4];
1267 if (!target->type->examined)
1268 {
1269 LOG_ERROR("Target not examined yet");
1270 return ERROR_FAIL;
1271 }
1272
1273 int retval = target->type->read_memory(target, address, 4, 1, value_buf);
1274
1275 if (retval == ERROR_OK)
1276 {
1277 *value = target_buffer_get_u32(target, value_buf);
1278 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address, *value);
1279 }
1280 else
1281 {
1282 *value = 0x0;
1283 LOG_DEBUG("address: 0x%8.8x failed", address);
1284 }
1285
1286 return retval;
1287 }
1288
1289 int target_read_u16(struct target_s *target, u32 address, u16 *value)
1290 {
1291 u8 value_buf[2];
1292 if (!target->type->examined)
1293 {
1294 LOG_ERROR("Target not examined yet");
1295 return ERROR_FAIL;
1296 }
1297
1298 int retval = target->type->read_memory(target, address, 2, 1, value_buf);
1299
1300 if (retval == ERROR_OK)
1301 {
1302 *value = target_buffer_get_u16(target, value_buf);
1303 LOG_DEBUG("address: 0x%8.8x, value: 0x%4.4x", address, *value);
1304 }
1305 else
1306 {
1307 *value = 0x0;
1308 LOG_DEBUG("address: 0x%8.8x failed", address);
1309 }
1310
1311 return retval;
1312 }
1313
1314 int target_read_u8(struct target_s *target, u32 address, u8 *value)
1315 {
1316 int retval = target->type->read_memory(target, address, 1, 1, value);
1317 if (!target->type->examined)
1318 {
1319 LOG_ERROR("Target not examined yet");
1320 return ERROR_FAIL;
1321 }
1322
1323 if (retval == ERROR_OK)
1324 {
1325 LOG_DEBUG("address: 0x%8.8x, value: 0x%2.2x", address, *value);
1326 }
1327 else
1328 {
1329 *value = 0x0;
1330 LOG_DEBUG("address: 0x%8.8x failed", address);
1331 }
1332
1333 return retval;
1334 }
1335
1336 int target_write_u32(struct target_s *target, u32 address, u32 value)
1337 {
1338 int retval;
1339 u8 value_buf[4];
1340 if (!target->type->examined)
1341 {
1342 LOG_ERROR("Target not examined yet");
1343 return ERROR_FAIL;
1344 }
1345
1346 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address, value);
1347
1348 target_buffer_set_u32(target, value_buf, value);
1349 if ((retval = target->type->write_memory(target, address, 4, 1, value_buf)) != ERROR_OK)
1350 {
1351 LOG_DEBUG("failed: %i", retval);
1352 }
1353
1354 return retval;
1355 }
1356
1357 int target_write_u16(struct target_s *target, u32 address, u16 value)
1358 {
1359 int retval;
1360 u8 value_buf[2];
1361 if (!target->type->examined)
1362 {
1363 LOG_ERROR("Target not examined yet");
1364 return ERROR_FAIL;
1365 }
1366
1367 LOG_DEBUG("address: 0x%8.8x, value: 0x%8.8x", address, value);
1368
1369 target_buffer_set_u16(target, value_buf, value);
1370 if ((retval = target->type->write_memory(target, address, 2, 1, value_buf)) != ERROR_OK)
1371 {
1372 LOG_DEBUG("failed: %i", retval);
1373 }
1374
1375 return retval;
1376 }
1377
1378 int target_write_u8(struct target_s *target, u32 address, u8 value)
1379 {
1380 int retval;
1381 if (!target->type->examined)
1382 {
1383 LOG_ERROR("Target not examined yet");
1384 return ERROR_FAIL;
1385 }
1386
1387 LOG_DEBUG("address: 0x%8.8x, value: 0x%2.2x", address, value);
1388
1389 if ((retval = target->type->read_memory(target, address, 1, 1, &value)) != ERROR_OK)
1390 {
1391 LOG_DEBUG("failed: %i", retval);
1392 }
1393
1394 return retval;
1395 }
1396
1397 int target_register_user_commands(struct command_context_s *cmd_ctx)
1398 {
1399 register_command(cmd_ctx, NULL, "reg", handle_reg_command, COMMAND_EXEC, NULL);
1400 register_command(cmd_ctx, NULL, "poll", handle_poll_command, COMMAND_EXEC, "poll target state");
1401 register_command(cmd_ctx, NULL, "wait_halt", handle_wait_halt_command, COMMAND_EXEC, "wait for target halt [time (s)]");
1402 register_command(cmd_ctx, NULL, "halt", handle_halt_command, COMMAND_EXEC, "halt target");
1403 register_command(cmd_ctx, NULL, "resume", handle_resume_command, COMMAND_EXEC, "resume target [addr]");
1404 register_command(cmd_ctx, NULL, "step", handle_step_command, COMMAND_EXEC, "step one instruction from current PC or [addr]");
1405 register_command(cmd_ctx, NULL, "NEWreset", handle_NEWreset_command, COMMAND_EXEC, "reset target [run|halt|init] - default is run");
1406 register_command(cmd_ctx, NULL, "reset", handle_reset_command, COMMAND_EXEC, "OLDreset target [run|halt|init] - default is run");
1407 register_command(cmd_ctx, NULL, "soft_reset_halt", handle_soft_reset_halt_command, COMMAND_EXEC, "halt the target and do a soft reset");
1408
1409 register_command(cmd_ctx, NULL, "mdw", handle_md_command, COMMAND_EXEC, "display memory words <addr> [count]");
1410 register_command(cmd_ctx, NULL, "mdh", handle_md_command, COMMAND_EXEC, "display memory half-words <addr> [count]");
1411 register_command(cmd_ctx, NULL, "mdb", handle_md_command, COMMAND_EXEC, "display memory bytes <addr> [count]");
1412
1413 register_command(cmd_ctx, NULL, "mww", handle_mw_command, COMMAND_EXEC, "write memory word <addr> <value> [count]");
1414 register_command(cmd_ctx, NULL, "mwh", handle_mw_command, COMMAND_EXEC, "write memory half-word <addr> <value> [count]");
1415 register_command(cmd_ctx, NULL, "mwb", handle_mw_command, COMMAND_EXEC, "write memory byte <addr> <value> [count]");
1416
1417 register_command(cmd_ctx, NULL, "bp", handle_bp_command, COMMAND_EXEC, "set breakpoint <address> <length> [hw]");
1418 register_command(cmd_ctx, NULL, "rbp", handle_rbp_command, COMMAND_EXEC, "remove breakpoint <adress>");
1419 register_command(cmd_ctx, NULL, "wp", handle_wp_command, COMMAND_EXEC, "set watchpoint <address> <length> <r/w/a> [value] [mask]");
1420 register_command(cmd_ctx, NULL, "rwp", handle_rwp_command, COMMAND_EXEC, "remove watchpoint <adress>");
1421
1422 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]");
1423 register_command(cmd_ctx, NULL, "dump_image", handle_dump_image_command, COMMAND_EXEC, "dump_image <file> <address> <size>");
1424 register_command(cmd_ctx, NULL, "verify_image", handle_verify_image_command, COMMAND_EXEC, "verify_image <file> [offset] [type]");
1425
1426 target_request_register_commands(cmd_ctx);
1427 trace_register_commands(cmd_ctx);
1428
1429 return ERROR_OK;
1430 }
1431
1432 int handle_targets_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1433 {
1434 char *cp;
1435 target_t *target = all_targets;
1436
1437 if (argc == 1)
1438 {
1439 /* try as tcltarget name */
1440 for( target = all_targets ; target ; target++ ){
1441 if( target->cmd_name ){
1442 if( 0 == strcmp( args[0], target->cmd_name ) ){
1443 /* MATCH */
1444 goto Match;
1445 }
1446 }
1447 }
1448 /* no match, try as number */
1449
1450 int num = strtoul(args[0], &cp, 0 );
1451 if( *cp != 0 ){
1452 /* then it was not a number */
1453 command_print( cmd_ctx, "Target: %s unknown, try one of:\n", args[0] );
1454 goto DumpTargets;
1455 }
1456
1457 target = get_target_by_num( num );
1458 if( target == NULL ){
1459 command_print(cmd_ctx,"Target: %s is unknown, try one of:\n", args[0] );
1460 goto DumpTargets;
1461 }
1462 Match:
1463 cmd_ctx->current_target = target->target_number;
1464 return ERROR_OK;
1465 }
1466 DumpTargets:
1467
1468 command_print(cmd_ctx, " CmdName Type Endian ChainPos State ");
1469 command_print(cmd_ctx, "-- ---------- ---------- ---------- -------- ----------");
1470 while (target)
1471 {
1472 /* XX: abcdefghij abcdefghij abcdefghij abcdefghij */
1473 command_print(cmd_ctx, "%2d: %-10s %-10s %-10s %8d %s",
1474 target->target_number,
1475 target->cmd_name,
1476 target->type->name,
1477 Jim_Nvp_value2name_simple( nvp_target_endian, target->endianness )->name,
1478 target->chain_position,
1479 Jim_Nvp_value2name_simple( nvp_target_state, target->state )->name );
1480 target = target->next;
1481 }
1482
1483 return ERROR_OK;
1484 }
1485
1486
1487
1488 int handle_working_area_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1489 {
1490 target_t *target = NULL;
1491
1492 if ((argc < 4) || (argc > 5))
1493 {
1494 return ERROR_COMMAND_SYNTAX_ERROR;
1495 }
1496
1497 target = get_target_by_num(strtoul(args[0], NULL, 0));
1498 if (!target)
1499 {
1500 return ERROR_COMMAND_SYNTAX_ERROR;
1501 }
1502 target_free_all_working_areas(target);
1503
1504 target->working_area_phys = target->working_area_virt = strtoul(args[1], NULL, 0);
1505 if (argc == 5)
1506 {
1507 target->working_area_virt = strtoul(args[4], NULL, 0);
1508 }
1509 target->working_area_size = strtoul(args[2], NULL, 0);
1510
1511 if (strcmp(args[3], "backup") == 0)
1512 {
1513 target->backup_working_area = 1;
1514 }
1515 else if (strcmp(args[3], "nobackup") == 0)
1516 {
1517 target->backup_working_area = 0;
1518 }
1519 else
1520 {
1521 LOG_ERROR("unrecognized <backup|nobackup> argument (%s)", args[3]);
1522 return ERROR_COMMAND_SYNTAX_ERROR;
1523 }
1524
1525 return ERROR_OK;
1526 }
1527
1528
1529 /* process target state changes */
1530 int handle_target(void *priv)
1531 {
1532 target_t *target = all_targets;
1533
1534 while (target)
1535 {
1536 if (target_continous_poll)
1537 {
1538 /* polling may fail silently until the target has been examined */
1539 target_poll(target);
1540 }
1541
1542 target = target->next;
1543 }
1544
1545 return ERROR_OK;
1546 }
1547
1548 int handle_reg_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1549 {
1550 target_t *target;
1551 reg_t *reg = NULL;
1552 int count = 0;
1553 char *value;
1554
1555 LOG_DEBUG("-");
1556
1557 target = get_current_target(cmd_ctx);
1558
1559 /* list all available registers for the current target */
1560 if (argc == 0)
1561 {
1562 reg_cache_t *cache = target->reg_cache;
1563
1564 count = 0;
1565 while(cache)
1566 {
1567 int i;
1568 for (i = 0; i < cache->num_regs; i++)
1569 {
1570 value = buf_to_str(cache->reg_list[i].value, cache->reg_list[i].size, 16);
1571 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);
1572 free(value);
1573 }
1574 cache = cache->next;
1575 }
1576
1577 return ERROR_OK;
1578 }
1579
1580 /* access a single register by its ordinal number */
1581 if ((args[0][0] >= '0') && (args[0][0] <= '9'))
1582 {
1583 int num = strtoul(args[0], NULL, 0);
1584 reg_cache_t *cache = target->reg_cache;
1585
1586 count = 0;
1587 while(cache)
1588 {
1589 int i;
1590 for (i = 0; i < cache->num_regs; i++)
1591 {
1592 if (count++ == num)
1593 {
1594 reg = &cache->reg_list[i];
1595 break;
1596 }
1597 }
1598 if (reg)
1599 break;
1600 cache = cache->next;
1601 }
1602
1603 if (!reg)
1604 {
1605 command_print(cmd_ctx, "%i is out of bounds, the current target has only %i registers (0 - %i)", num, count, count - 1);
1606 return ERROR_OK;
1607 }
1608 } else /* access a single register by its name */
1609 {
1610 reg = register_get_by_name(target->reg_cache, args[0], 1);
1611
1612 if (!reg)
1613 {
1614 command_print(cmd_ctx, "register %s not found in current target", args[0]);
1615 return ERROR_OK;
1616 }
1617 }
1618
1619 /* display a register */
1620 if ((argc == 1) || ((argc == 2) && !((args[1][0] >= '0') && (args[1][0] <= '9'))))
1621 {
1622 if ((argc == 2) && (strcmp(args[1], "force") == 0))
1623 reg->valid = 0;
1624
1625 if (reg->valid == 0)
1626 {
1627 reg_arch_type_t *arch_type = register_get_arch_type(reg->arch_type);
1628 if (arch_type == NULL)
1629 {
1630 LOG_ERROR("BUG: encountered unregistered arch type");
1631 return ERROR_OK;
1632 }
1633 arch_type->get(reg);
1634 }
1635 value = buf_to_str(reg->value, reg->size, 16);
1636 command_print(cmd_ctx, "%s (/%i): 0x%s", reg->name, reg->size, value);
1637 free(value);
1638 return ERROR_OK;
1639 }
1640
1641 /* set register value */
1642 if (argc == 2)
1643 {
1644 u8 *buf = malloc(CEIL(reg->size, 8));
1645 str_to_buf(args[1], strlen(args[1]), buf, reg->size, 0);
1646
1647 reg_arch_type_t *arch_type = register_get_arch_type(reg->arch_type);
1648 if (arch_type == NULL)
1649 {
1650 LOG_ERROR("BUG: encountered unregistered arch type");
1651 return ERROR_OK;
1652 }
1653
1654 arch_type->set(reg, buf);
1655
1656 value = buf_to_str(reg->value, reg->size, 16);
1657 command_print(cmd_ctx, "%s (/%i): 0x%s", reg->name, reg->size, value);
1658 free(value);
1659
1660 free(buf);
1661
1662 return ERROR_OK;
1663 }
1664
1665 command_print(cmd_ctx, "usage: reg <#|name> [value]");
1666
1667 return ERROR_OK;
1668 }
1669
1670
1671 int handle_poll_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1672 {
1673 target_t *target = get_current_target(cmd_ctx);
1674
1675 if (argc == 0)
1676 {
1677 target_poll(target);
1678 target_arch_state(target);
1679 }
1680 else
1681 {
1682 if (strcmp(args[0], "on") == 0)
1683 {
1684 target_continous_poll = 1;
1685 }
1686 else if (strcmp(args[0], "off") == 0)
1687 {
1688 target_continous_poll = 0;
1689 }
1690 else
1691 {
1692 command_print(cmd_ctx, "arg is \"on\" or \"off\"");
1693 }
1694 }
1695
1696
1697 return ERROR_OK;
1698 }
1699
1700 int handle_wait_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1701 {
1702 int ms = 5000;
1703
1704 if (argc > 0)
1705 {
1706 char *end;
1707
1708 ms = strtoul(args[0], &end, 0) * 1000;
1709 if (*end)
1710 {
1711 command_print(cmd_ctx, "usage: %s [seconds]", cmd);
1712 return ERROR_OK;
1713 }
1714 }
1715 target_t *target = get_current_target(cmd_ctx);
1716
1717 return target_wait_state(target, TARGET_HALTED, ms);
1718 }
1719
1720 int target_wait_state(target_t *target, enum target_state state, int ms)
1721 {
1722 int retval;
1723 struct timeval timeout, now;
1724 int once=1;
1725 gettimeofday(&timeout, NULL);
1726 timeval_add_time(&timeout, 0, ms * 1000);
1727
1728 for (;;)
1729 {
1730 if ((retval=target_poll(target))!=ERROR_OK)
1731 return retval;
1732 keep_alive();
1733 if (target->state == state)
1734 {
1735 break;
1736 }
1737 if (once)
1738 {
1739 once=0;
1740 LOG_DEBUG("waiting for target %s...",
1741 Jim_Nvp_value2name_simple(nvp_target_state,state)->name);
1742 }
1743
1744 gettimeofday(&now, NULL);
1745 if ((now.tv_sec > timeout.tv_sec) || ((now.tv_sec == timeout.tv_sec) && (now.tv_usec >= timeout.tv_usec)))
1746 {
1747 LOG_ERROR("timed out while waiting for target %s",
1748 Jim_Nvp_value2name_simple(nvp_target_state,state)->name);
1749 return ERROR_FAIL;
1750 }
1751 }
1752
1753 return ERROR_OK;
1754 }
1755
1756 int handle_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1757 {
1758 int retval;
1759 target_t *target = get_current_target(cmd_ctx);
1760
1761 LOG_DEBUG("-");
1762
1763 if ((retval = target_halt(target)) != ERROR_OK)
1764 {
1765 return retval;
1766 }
1767
1768 return handle_wait_halt_command(cmd_ctx, cmd, args, argc);
1769 }
1770
1771 int handle_soft_reset_halt_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1772 {
1773 target_t *target = get_current_target(cmd_ctx);
1774
1775 LOG_USER("requesting target halt and executing a soft reset");
1776
1777 target->type->soft_reset_halt(target);
1778
1779 return ERROR_OK;
1780 }
1781
1782 int handle_reset_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1783 {
1784 const Jim_Nvp *n;
1785 enum target_reset_mode reset_mode = RESET_RUN;
1786
1787 if (argc >= 1)
1788 {
1789 n = Jim_Nvp_name2value_simple( nvp_reset_modes, args[0] );
1790 if( (n->name == NULL) || (n->value == RESET_UNKNOWN) ){
1791 return ERROR_COMMAND_SYNTAX_ERROR;
1792 }
1793 reset_mode = n->value;
1794 }
1795
1796 /* reset *all* targets */
1797 return target_process_reset(cmd_ctx, reset_mode);
1798 }
1799
1800 int handle_NEWreset_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1801 {
1802 int x;
1803 char *cp;
1804
1805 if (argc >= 1){
1806 x = strtol( args[0], &cp, 0 );
1807 if( *cp != 0 ){
1808 command_print( cmd_ctx, "Not numeric: %s\n", args[0] );
1809 return ERROR_COMMAND_SYNTAX_ERROR;
1810 }
1811 USE_OLD_RESET = !!x;
1812 }
1813 command_print( cmd_ctx, "reset method: %d (%s)\n",
1814 USE_OLD_RESET,
1815 USE_OLD_RESET ? "old-method" : "new-method" );
1816 return ERROR_OK;
1817 }
1818
1819 int handle_resume_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1820 {
1821 int retval;
1822 target_t *target = get_current_target(cmd_ctx);
1823
1824 target_handle_event( target, TARGET_EVENT_OLD_pre_resume );
1825
1826 if (argc == 0)
1827 retval = target_resume(target, 1, 0, 1, 0); /* current pc, addr = 0, handle breakpoints, not debugging */
1828 else if (argc == 1)
1829 retval = target_resume(target, 0, strtoul(args[0], NULL, 0), 1, 0); /* addr = args[0], handle breakpoints, not debugging */
1830 else
1831 {
1832 retval = ERROR_COMMAND_SYNTAX_ERROR;
1833 }
1834
1835 return retval;
1836 }
1837
1838 int handle_step_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1839 {
1840 target_t *target = get_current_target(cmd_ctx);
1841
1842 LOG_DEBUG("-");
1843
1844 if (argc == 0)
1845 target->type->step(target, 1, 0, 1); /* current pc, addr = 0, handle breakpoints */
1846
1847 if (argc == 1)
1848 target->type->step(target, 0, strtoul(args[0], NULL, 0), 1); /* addr = args[0], handle breakpoints */
1849
1850 return ERROR_OK;
1851 }
1852
1853 int handle_md_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1854 {
1855 const int line_bytecnt = 32;
1856 int count = 1;
1857 int size = 4;
1858 u32 address = 0;
1859 int line_modulo;
1860 int i;
1861
1862 char output[128];
1863 int output_len;
1864
1865 int retval;
1866
1867 u8 *buffer;
1868 target_t *target = get_current_target(cmd_ctx);
1869
1870 if (argc < 1)
1871 return ERROR_OK;
1872
1873 if (argc == 2)
1874 count = strtoul(args[1], NULL, 0);
1875
1876 address = strtoul(args[0], NULL, 0);
1877
1878
1879 switch (cmd[2])
1880 {
1881 case 'w':
1882 size = 4; line_modulo = line_bytecnt / 4;
1883 break;
1884 case 'h':
1885 size = 2; line_modulo = line_bytecnt / 2;
1886 break;
1887 case 'b':
1888 size = 1; line_modulo = line_bytecnt / 1;
1889 break;
1890 default:
1891 return ERROR_OK;
1892 }
1893
1894 buffer = calloc(count, size);
1895 retval = target->type->read_memory(target, address, size, count, buffer);
1896 if (retval == ERROR_OK)
1897 {
1898 output_len = 0;
1899
1900 for (i = 0; i < count; i++)
1901 {
1902 if (i%line_modulo == 0)
1903 output_len += snprintf(output + output_len, 128 - output_len, "0x%8.8x: ", address + (i*size));
1904
1905 switch (size)
1906 {
1907 case 4:
1908 output_len += snprintf(output + output_len, 128 - output_len, "%8.8x ", target_buffer_get_u32(target, &buffer[i*4]));
1909 break;
1910 case 2:
1911 output_len += snprintf(output + output_len, 128 - output_len, "%4.4x ", target_buffer_get_u16(target, &buffer[i*2]));
1912 break;
1913 case 1:
1914 output_len += snprintf(output + output_len, 128 - output_len, "%2.2x ", buffer[i*1]);
1915 break;
1916 }
1917
1918 if ((i%line_modulo == line_modulo-1) || (i == count - 1))
1919 {
1920 command_print(cmd_ctx, output);
1921 output_len = 0;
1922 }
1923 }
1924 }
1925
1926 free(buffer);
1927
1928 return retval;
1929 }
1930
1931 int handle_mw_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1932 {
1933 u32 address = 0;
1934 u32 value = 0;
1935 int count = 1;
1936 int i;
1937 int wordsize;
1938 target_t *target = get_current_target(cmd_ctx);
1939 u8 value_buf[4];
1940
1941 if ((argc < 2) || (argc > 3))
1942 return ERROR_COMMAND_SYNTAX_ERROR;
1943
1944 address = strtoul(args[0], NULL, 0);
1945 value = strtoul(args[1], NULL, 0);
1946 if (argc == 3)
1947 count = strtoul(args[2], NULL, 0);
1948
1949 switch (cmd[2])
1950 {
1951 case 'w':
1952 wordsize = 4;
1953 target_buffer_set_u32(target, value_buf, value);
1954 break;
1955 case 'h':
1956 wordsize = 2;
1957 target_buffer_set_u16(target, value_buf, value);
1958 break;
1959 case 'b':
1960 wordsize = 1;
1961 value_buf[0] = value;
1962 break;
1963 default:
1964 return ERROR_COMMAND_SYNTAX_ERROR;
1965 }
1966 for (i=0; i<count; i++)
1967 {
1968 int retval;
1969 switch (wordsize)
1970 {
1971 case 4:
1972 retval = target->type->write_memory(target, address + i*wordsize, 4, 1, value_buf);
1973 break;
1974 case 2:
1975 retval = target->type->write_memory(target, address + i*wordsize, 2, 1, value_buf);
1976 break;
1977 case 1:
1978 retval = target->type->write_memory(target, address + i*wordsize, 1, 1, value_buf);
1979 break;
1980 default:
1981 return ERROR_OK;
1982 }
1983 if (retval!=ERROR_OK)
1984 {
1985 return retval;
1986 }
1987 }
1988
1989 return ERROR_OK;
1990
1991 }
1992
1993 int handle_load_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
1994 {
1995 u8 *buffer;
1996 u32 buf_cnt;
1997 u32 image_size;
1998 u32 min_address=0;
1999 u32 max_address=0xffffffff;
2000 int i;
2001 int retval;
2002
2003 image_t image;
2004
2005 duration_t duration;
2006 char *duration_text;
2007
2008 target_t *target = get_current_target(cmd_ctx);
2009
2010 if ((argc < 1)||(argc > 5))
2011 {
2012 return ERROR_COMMAND_SYNTAX_ERROR;
2013 }
2014
2015 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
2016 if (argc >= 2)
2017 {
2018 image.base_address_set = 1;
2019 image.base_address = strtoul(args[1], NULL, 0);
2020 }
2021 else
2022 {
2023 image.base_address_set = 0;
2024 }
2025
2026
2027 image.start_address_set = 0;
2028
2029 if (argc>=4)
2030 {
2031 min_address=strtoul(args[3], NULL, 0);
2032 }
2033 if (argc>=5)
2034 {
2035 max_address=strtoul(args[4], NULL, 0)+min_address;
2036 }
2037
2038 if (min_address>max_address)
2039 {
2040 return ERROR_COMMAND_SYNTAX_ERROR;
2041 }
2042
2043
2044 duration_start_measure(&duration);
2045
2046 if (image_open(&image, args[0], (argc >= 3) ? args[2] : NULL) != ERROR_OK)
2047 {
2048 return ERROR_OK;
2049 }
2050
2051 image_size = 0x0;
2052 retval = ERROR_OK;
2053 for (i = 0; i < image.num_sections; i++)
2054 {
2055 buffer = malloc(image.sections[i].size);
2056 if (buffer == NULL)
2057 {
2058 command_print(cmd_ctx, "error allocating buffer for section (%d bytes)", image.sections[i].size);
2059 break;
2060 }
2061
2062 if ((retval = image_read_section(&image, i, 0x0, image.sections[i].size, buffer, &buf_cnt)) != ERROR_OK)
2063 {
2064 free(buffer);
2065 break;
2066 }
2067
2068 u32 offset=0;
2069 u32 length=buf_cnt;
2070
2071
2072 /* DANGER!!! beware of unsigned comparision here!!! */
2073
2074 if ((image.sections[i].base_address+buf_cnt>=min_address)&&
2075 (image.sections[i].base_address<max_address))
2076 {
2077 if (image.sections[i].base_address<min_address)
2078 {
2079 /* clip addresses below */
2080 offset+=min_address-image.sections[i].base_address;
2081 length-=offset;
2082 }
2083
2084 if (image.sections[i].base_address+buf_cnt>max_address)
2085 {
2086 length-=(image.sections[i].base_address+buf_cnt)-max_address;
2087 }
2088
2089 if ((retval = target_write_buffer(target, image.sections[i].base_address+offset, length, buffer+offset)) != ERROR_OK)
2090 {
2091 free(buffer);
2092 break;
2093 }
2094 image_size += length;
2095 command_print(cmd_ctx, "%u byte written at address 0x%8.8x", length, image.sections[i].base_address+offset);
2096 }
2097
2098 free(buffer);
2099 }
2100
2101 duration_stop_measure(&duration, &duration_text);
2102 if (retval==ERROR_OK)
2103 {
2104 command_print(cmd_ctx, "downloaded %u byte in %s", image_size, duration_text);
2105 }
2106 free(duration_text);
2107
2108 image_close(&image);
2109
2110 return retval;
2111
2112 }
2113
2114 int handle_dump_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2115 {
2116 fileio_t fileio;
2117
2118 u32 address;
2119 u32 size;
2120 u8 buffer[560];
2121 int retval=ERROR_OK;
2122
2123 duration_t duration;
2124 char *duration_text;
2125
2126 target_t *target = get_current_target(cmd_ctx);
2127
2128 if (argc != 3)
2129 {
2130 command_print(cmd_ctx, "usage: dump_image <filename> <address> <size>");
2131 return ERROR_OK;
2132 }
2133
2134 address = strtoul(args[1], NULL, 0);
2135 size = strtoul(args[2], NULL, 0);
2136
2137 if ((address & 3) || (size & 3))
2138 {
2139 command_print(cmd_ctx, "only 32-bit aligned address and size are supported");
2140 return ERROR_OK;
2141 }
2142
2143 if (fileio_open(&fileio, args[0], FILEIO_WRITE, FILEIO_BINARY) != ERROR_OK)
2144 {
2145 return ERROR_OK;
2146 }
2147
2148 duration_start_measure(&duration);
2149
2150 while (size > 0)
2151 {
2152 u32 size_written;
2153 u32 this_run_size = (size > 560) ? 560 : size;
2154
2155 retval = target->type->read_memory(target, address, 4, this_run_size / 4, buffer);
2156 if (retval != ERROR_OK)
2157 {
2158 break;
2159 }
2160
2161 retval = fileio_write(&fileio, this_run_size, buffer, &size_written);
2162 if (retval != ERROR_OK)
2163 {
2164 break;
2165 }
2166
2167 size -= this_run_size;
2168 address += this_run_size;
2169 }
2170
2171 fileio_close(&fileio);
2172
2173 duration_stop_measure(&duration, &duration_text);
2174 if (retval==ERROR_OK)
2175 {
2176 command_print(cmd_ctx, "dumped %"PRIi64" byte in %s", fileio.size, duration_text);
2177 }
2178 free(duration_text);
2179
2180 return ERROR_OK;
2181 }
2182
2183 int handle_verify_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2184 {
2185 u8 *buffer;
2186 u32 buf_cnt;
2187 u32 image_size;
2188 int i;
2189 int retval;
2190 u32 checksum = 0;
2191 u32 mem_checksum = 0;
2192
2193 image_t image;
2194
2195 duration_t duration;
2196 char *duration_text;
2197
2198 target_t *target = get_current_target(cmd_ctx);
2199
2200 if (argc < 1)
2201 {
2202 return ERROR_COMMAND_SYNTAX_ERROR;
2203 }
2204
2205 if (!target)
2206 {
2207 LOG_ERROR("no target selected");
2208 return ERROR_FAIL;
2209 }
2210
2211 duration_start_measure(&duration);
2212
2213 if (argc >= 2)
2214 {
2215 image.base_address_set = 1;
2216 image.base_address = strtoul(args[1], NULL, 0);
2217 }
2218 else
2219 {
2220 image.base_address_set = 0;
2221 image.base_address = 0x0;
2222 }
2223
2224 image.start_address_set = 0;
2225
2226 if ((retval=image_open(&image, args[0], (argc == 3) ? args[2] : NULL)) != ERROR_OK)
2227 {
2228 return retval;
2229 }
2230
2231 image_size = 0x0;
2232 retval=ERROR_OK;
2233 for (i = 0; i < image.num_sections; i++)
2234 {
2235 buffer = malloc(image.sections[i].size);
2236 if (buffer == NULL)
2237 {
2238 command_print(cmd_ctx, "error allocating buffer for section (%d bytes)", image.sections[i].size);
2239 break;
2240 }
2241 if ((retval = image_read_section(&image, i, 0x0, image.sections[i].size, buffer, &buf_cnt)) != ERROR_OK)
2242 {
2243 free(buffer);
2244 break;
2245 }
2246
2247 /* calculate checksum of image */
2248 image_calculate_checksum( buffer, buf_cnt, &checksum );
2249
2250 retval = target_checksum_memory(target, image.sections[i].base_address, buf_cnt, &mem_checksum);
2251 if( retval != ERROR_OK )
2252 {
2253 free(buffer);
2254 break;
2255 }
2256
2257 if( checksum != mem_checksum )
2258 {
2259 /* failed crc checksum, fall back to a binary compare */
2260 u8 *data;
2261
2262 command_print(cmd_ctx, "checksum mismatch - attempting binary compare");
2263
2264 data = (u8*)malloc(buf_cnt);
2265
2266 /* Can we use 32bit word accesses? */
2267 int size = 1;
2268 int count = buf_cnt;
2269 if ((count % 4) == 0)
2270 {
2271 size *= 4;
2272 count /= 4;
2273 }
2274 retval = target->type->read_memory(target, image.sections[i].base_address, size, count, data);
2275 if (retval == ERROR_OK)
2276 {
2277 int t;
2278 for (t = 0; t < buf_cnt; t++)
2279 {
2280 if (data[t] != buffer[t])
2281 {
2282 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]);
2283 free(data);
2284 free(buffer);
2285 retval=ERROR_FAIL;
2286 goto done;
2287 }
2288 if ((t%16384)==0)
2289 {
2290 keep_alive();
2291 }
2292 }
2293 }
2294
2295 free(data);
2296 }
2297
2298 free(buffer);
2299 image_size += buf_cnt;
2300 }
2301 done:
2302 duration_stop_measure(&duration, &duration_text);
2303 if (retval==ERROR_OK)
2304 {
2305 command_print(cmd_ctx, "verified %u bytes in %s", image_size, duration_text);
2306 }
2307 free(duration_text);
2308
2309 image_close(&image);
2310
2311 return retval;
2312 }
2313
2314 int handle_bp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2315 {
2316 int retval;
2317 target_t *target = get_current_target(cmd_ctx);
2318
2319 if (argc == 0)
2320 {
2321 breakpoint_t *breakpoint = target->breakpoints;
2322
2323 while (breakpoint)
2324 {
2325 if (breakpoint->type == BKPT_SOFT)
2326 {
2327 char* buf = buf_to_str(breakpoint->orig_instr, breakpoint->length, 16);
2328 command_print(cmd_ctx, "0x%8.8x, 0x%x, %i, 0x%s", breakpoint->address, breakpoint->length, breakpoint->set, buf);
2329 free(buf);
2330 }
2331 else
2332 {
2333 command_print(cmd_ctx, "0x%8.8x, 0x%x, %i", breakpoint->address, breakpoint->length, breakpoint->set);
2334 }
2335 breakpoint = breakpoint->next;
2336 }
2337 }
2338 else if (argc >= 2)
2339 {
2340 int hw = BKPT_SOFT;
2341 u32 length = 0;
2342
2343 length = strtoul(args[1], NULL, 0);
2344
2345 if (argc >= 3)
2346 if (strcmp(args[2], "hw") == 0)
2347 hw = BKPT_HARD;
2348
2349 if ((retval = breakpoint_add(target, strtoul(args[0], NULL, 0), length, hw)) != ERROR_OK)
2350 {
2351 LOG_ERROR("Failure setting breakpoints");
2352 }
2353 else
2354 {
2355 command_print(cmd_ctx, "breakpoint added at address 0x%8.8x", strtoul(args[0], NULL, 0));
2356 }
2357 }
2358 else
2359 {
2360 command_print(cmd_ctx, "usage: bp <address> <length> ['hw']");
2361 }
2362
2363 return ERROR_OK;
2364 }
2365
2366 int handle_rbp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2367 {
2368 target_t *target = get_current_target(cmd_ctx);
2369
2370 if (argc > 0)
2371 breakpoint_remove(target, strtoul(args[0], NULL, 0));
2372
2373 return ERROR_OK;
2374 }
2375
2376 int handle_wp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2377 {
2378 target_t *target = get_current_target(cmd_ctx);
2379 int retval;
2380
2381 if (argc == 0)
2382 {
2383 watchpoint_t *watchpoint = target->watchpoints;
2384
2385 while (watchpoint)
2386 {
2387 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);
2388 watchpoint = watchpoint->next;
2389 }
2390 }
2391 else if (argc >= 2)
2392 {
2393 enum watchpoint_rw type = WPT_ACCESS;
2394 u32 data_value = 0x0;
2395 u32 data_mask = 0xffffffff;
2396
2397 if (argc >= 3)
2398 {
2399 switch(args[2][0])
2400 {
2401 case 'r':
2402 type = WPT_READ;
2403 break;
2404 case 'w':
2405 type = WPT_WRITE;
2406 break;
2407 case 'a':
2408 type = WPT_ACCESS;
2409 break;
2410 default:
2411 command_print(cmd_ctx, "usage: wp <address> <length> [r/w/a] [value] [mask]");
2412 return ERROR_OK;
2413 }
2414 }
2415 if (argc >= 4)
2416 {
2417 data_value = strtoul(args[3], NULL, 0);
2418 }
2419 if (argc >= 5)
2420 {
2421 data_mask = strtoul(args[4], NULL, 0);
2422 }
2423
2424 if ((retval = watchpoint_add(target, strtoul(args[0], NULL, 0),
2425 strtoul(args[1], NULL, 0), type, data_value, data_mask)) != ERROR_OK)
2426 {
2427 LOG_ERROR("Failure setting breakpoints");
2428 }
2429 }
2430 else
2431 {
2432 command_print(cmd_ctx, "usage: wp <address> <length> [r/w/a] [value] [mask]");
2433 }
2434
2435 return ERROR_OK;
2436 }
2437
2438 int handle_rwp_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2439 {
2440 target_t *target = get_current_target(cmd_ctx);
2441
2442 if (argc > 0)
2443 watchpoint_remove(target, strtoul(args[0], NULL, 0));
2444
2445 return ERROR_OK;
2446 }
2447
2448 int handle_virt2phys_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
2449 {
2450 int retval;
2451 target_t *target = get_current_target(cmd_ctx);
2452 u32 va;
2453 u32 pa;
2454
2455 if (argc != 1)
2456 {
2457 return ERROR_COMMAND_SYNTAX_ERROR;
2458 }
2459 va = strtoul(args[0], NULL, 0);
2460
2461 retval = target->type->virt2phys(target, va, &pa);
2462 if (retval == ERROR_OK)
2463 {
2464 command_print(cmd_ctx, "Physical address 0x%08x", pa);
2465 }
2466 else
2467 {
2468 /* lower levels will have logged a detailed error which is
2469 * forwarded to telnet/GDB session.
2470 */
2471 }
2472 return retval;
2473 }
2474 static void writeLong(FILE *f, int l)
2475 {
2476 int i;
2477 for (i=0; i<4; i++)
2478 {
2479 char c=(l>>(i*8))&0xff;
2480 fwrite(&c, 1, 1, f);
2481 }
2482
2483 }
2484 static void writeString(FILE *f, char *s)
2485 {
2486 fwrite(s, 1, strlen(s), f);
2487 }
2488
2489
2490
2491 // Dump a gmon.out histogram file.
2492 static void writeGmon(u32 *samples, int sampleNum, char *filename)
2493 {
2494 int i;
2495 FILE *f=fopen(filename, "w");
2496 if (f==NULL)
2497 return;
2498 fwrite("gmon", 1, 4, f);
2499 writeLong(f, 0x00000001); // Version
2500 writeLong(f, 0); // padding
2501 writeLong(f, 0); // padding
2502 writeLong(f, 0); // padding
2503
2504 fwrite("", 1, 1, f); // GMON_TAG_TIME_HIST
2505
2506 // figure out bucket size
2507 u32 min=samples[0];
2508 u32 max=samples[0];
2509 for (i=0; i<sampleNum; i++)
2510 {
2511 if (min>samples[i])
2512 {
2513 min=samples[i];
2514 }
2515 if (max<samples[i])
2516 {
2517 max=samples[i];
2518 }
2519 }
2520
2521 int addressSpace=(max-min+1);
2522
2523 static int const maxBuckets=256*1024; // maximum buckets.
2524 int length=addressSpace;
2525 if (length > maxBuckets)
2526 {
2527 length=maxBuckets;
2528 }
2529 int *buckets=malloc(sizeof(int)*length);
2530 if (buckets==NULL)
2531 {
2532 fclose(f);
2533 return;
2534 }
2535 memset(buckets, 0, sizeof(int)*length);
2536 for (i=0; i<sampleNum;i++)
2537 {
2538 u32 address=samples[i];
2539 long long a=address-min;
2540 long long b=length-1;
2541 long long c=addressSpace-1;
2542 int index=(a*b)/c; // danger!!!! int32 overflows
2543 buckets[index]++;
2544 }
2545
2546 // append binary memory gmon.out &profile_hist_hdr ((char*)&profile_hist_hdr + sizeof(struct gmon_hist_hdr))
2547 writeLong(f, min); // low_pc
2548 writeLong(f, max); // high_pc
2549 writeLong(f, length); // # of samples
2550 writeLong(f, 64000000); // 64MHz
2551 writeString(f, "seconds");
2552 for (i=0; i<(15-strlen("seconds")); i++)
2553 {
2554 fwrite("", 1, 1, f); // padding
2555 }
2556 writeString(f, "s");
2557
2558 // append binary memory gmon.out profile_hist_data (profile_hist_data + profile_hist_hdr.hist_size)
2559
2560 char *data=malloc(2*length);
2561 if (data!=NULL)
2562 {
2563 for (i=0; i<length;i++)
2564 {
2565 int val;
2566 val=buckets[i];
2567 if (val>65535)
2568 {
2569 val=65535;
2570 }
2571 data[i*2]=val&0xff;
2572 data[i*2+1]=(val>>8)&0xff;
2573 }
2574 free(buckets);
2575 fwrite(data, 1, length*2, f);
2576 free(data);
2577 } else
2578 {
2579 free(buckets);
2580 }
2581
2582 fclose(f);
2583 }
2584
2585 /* profiling samples the CPU PC as quickly as OpenOCD is able, which will be used as a random sampling of PC */
2586 int handle_profile_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
2587 {
2588 target_t *target = get_current_target(cmd_ctx);
2589 struct timeval timeout, now;
2590
2591 gettimeofday(&timeout, NULL);
2592 if (argc!=2)
2593 {
2594 return ERROR_COMMAND_SYNTAX_ERROR;
2595 }
2596 char *end;
2597 timeval_add_time(&timeout, strtoul(args[0], &end, 0), 0);
2598 if (*end)
2599 {
2600 return ERROR_OK;
2601 }
2602
2603 command_print(cmd_ctx, "Starting profiling. Halting and resuming the target as often as we can...");
2604
2605 static const int maxSample=10000;
2606 u32 *samples=malloc(sizeof(u32)*maxSample);
2607 if (samples==NULL)
2608 return ERROR_OK;
2609
2610 int numSamples=0;
2611 int retval=ERROR_OK;
2612 // hopefully it is safe to cache! We want to stop/restart as quickly as possible.
2613 reg_t *reg = register_get_by_name(target->reg_cache, "pc", 1);
2614
2615 for (;;)
2616 {
2617 target_poll(target);
2618 if (target->state == TARGET_HALTED)
2619 {
2620 u32 t=*((u32 *)reg->value);
2621 samples[numSamples++]=t;
2622 retval = target_resume(target, 1, 0, 0, 0); /* current pc, addr = 0, do not handle breakpoints, not debugging */
2623 target_poll(target);
2624 alive_sleep(10); // sleep 10ms, i.e. <100 samples/second.
2625 } else if (target->state == TARGET_RUNNING)
2626 {
2627 // We want to quickly sample the PC.
2628 target_halt(target);
2629 } else
2630 {
2631 command_print(cmd_ctx, "Target not halted or running");
2632 retval=ERROR_OK;
2633 break;
2634 }
2635 if (retval!=ERROR_OK)
2636 {
2637 break;
2638 }
2639
2640 gettimeofday(&now, NULL);
2641 if ((numSamples>=maxSample) || ((now.tv_sec >= timeout.tv_sec) && (now.tv_usec >= timeout.tv_usec)))
2642 {
2643 command_print(cmd_ctx, "Profiling completed. %d samples.", numSamples);
2644 target_poll(target);
2645 if (target->state == TARGET_HALTED)
2646 {
2647 target_resume(target, 1, 0, 0, 0); /* current pc, addr = 0, do not handle breakpoints, not debugging */
2648 }
2649 target_poll(target);
2650 writeGmon(samples, numSamples, args[1]);
2651 command_print(cmd_ctx, "Wrote %s", args[1]);
2652 break;
2653 }
2654 }
2655 free(samples);
2656
2657 return ERROR_OK;
2658 }
2659
2660 static int new_int_array_element(Jim_Interp * interp, const char *varname, int idx, u32 val)
2661 {
2662 char *namebuf;
2663 Jim_Obj *nameObjPtr, *valObjPtr;
2664 int result;
2665
2666 namebuf = alloc_printf("%s(%d)", varname, idx);
2667 if (!namebuf)
2668 return JIM_ERR;
2669
2670 nameObjPtr = Jim_NewStringObj(interp, namebuf, -1);
2671 valObjPtr = Jim_NewIntObj(interp, val);
2672 if (!nameObjPtr || !valObjPtr)
2673 {
2674 free(namebuf);
2675 return JIM_ERR;
2676 }
2677
2678 Jim_IncrRefCount(nameObjPtr);
2679 Jim_IncrRefCount(valObjPtr);
2680 result = Jim_SetVariable(interp, nameObjPtr, valObjPtr);
2681 Jim_DecrRefCount(interp, nameObjPtr);
2682 Jim_DecrRefCount(interp, valObjPtr);
2683 free(namebuf);
2684 /* printf("%s(%d) <= 0%08x\n", varname, idx, val); */
2685 return result;
2686 }
2687
2688 static int jim_mem2array(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
2689 {
2690 command_context_t *context;
2691 target_t *target;
2692
2693 context = Jim_GetAssocData(interp, "context");
2694 if (context == NULL)
2695 {
2696 LOG_ERROR("mem2array: no command context");
2697 return JIM_ERR;
2698 }
2699 target = get_current_target(context);
2700 if (target == NULL)
2701 {
2702 LOG_ERROR("mem2array: no current target");
2703 return JIM_ERR;
2704 }
2705
2706 return target_mem2array(interp, target, argc,argv);
2707 }
2708
2709 static int target_mem2array(Jim_Interp *interp, target_t *target, int argc, Jim_Obj *const *argv)
2710 {
2711 long l;
2712 u32 width;
2713 u32 len;
2714 u32 addr;
2715 u32 count;
2716 u32 v;
2717 const char *varname;
2718 u8 buffer[4096];
2719 int i, n, e, retval;
2720
2721 /* argv[1] = name of array to receive the data
2722 * argv[2] = desired width
2723 * argv[3] = memory address
2724 * argv[4] = count of times to read
2725 */
2726 if (argc != 5) {
2727 Jim_WrongNumArgs(interp, 1, argv, "varname width addr nelems");
2728 return JIM_ERR;
2729 }
2730 varname = Jim_GetString(argv[1], &len);
2731 /* given "foo" get space for worse case "foo(%d)" .. add 20 */
2732
2733 e = Jim_GetLong(interp, argv[2], &l);
2734 width = l;
2735 if (e != JIM_OK) {
2736 return e;
2737 }
2738
2739 e = Jim_GetLong(interp, argv[3], &l);
2740 addr = l;
2741 if (e != JIM_OK) {
2742 return e;
2743 }
2744 e = Jim_GetLong(interp, argv[4], &l);
2745 len = l;
2746 if (e != JIM_OK) {
2747 return e;
2748 }
2749 switch (width) {
2750 case 8:
2751 width = 1;
2752 break;
2753 case 16:
2754 width = 2;
2755 break;
2756 case 32:
2757 width = 4;
2758 break;
2759 default:
2760 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2761 Jim_AppendStrings( interp, Jim_GetResult(interp), "Invalid width param, must be 8/16/32", NULL );
2762 return JIM_ERR;
2763 }
2764 if (len == 0) {
2765 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2766 Jim_AppendStrings(interp, Jim_GetResult(interp), "mem2array: zero width read?", NULL);
2767 return JIM_ERR;
2768 }
2769 if ((addr + (len * width)) < addr) {
2770 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2771 Jim_AppendStrings(interp, Jim_GetResult(interp), "mem2array: addr + len - wraps to zero?", NULL);
2772 return JIM_ERR;
2773 }
2774 /* absurd transfer size? */
2775 if (len > 65536) {
2776 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2777 Jim_AppendStrings(interp, Jim_GetResult(interp), "mem2array: absurd > 64K item request", NULL);
2778 return JIM_ERR;
2779 }
2780
2781 if ((width == 1) ||
2782 ((width == 2) && ((addr & 1) == 0)) ||
2783 ((width == 4) && ((addr & 3) == 0))) {
2784 /* all is well */
2785 } else {
2786 char buf[100];
2787 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2788 sprintf(buf, "mem2array address: 0x%08x is not aligned for %d byte reads", addr, width);
2789 Jim_AppendStrings(interp, Jim_GetResult(interp), buf , NULL);
2790 return JIM_ERR;
2791 }
2792
2793 /* Transfer loop */
2794
2795 /* index counter */
2796 n = 0;
2797 /* assume ok */
2798 e = JIM_OK;
2799 while (len) {
2800 /* Slurp... in buffer size chunks */
2801
2802 count = len; /* in objects.. */
2803 if (count > (sizeof(buffer)/width)) {
2804 count = (sizeof(buffer)/width);
2805 }
2806
2807 retval = target->type->read_memory( target, addr, width, count, buffer );
2808 if (retval != ERROR_OK) {
2809 /* BOO !*/
2810 LOG_ERROR("mem2array: Read @ 0x%08x, w=%d, cnt=%d, failed", addr, width, count);
2811 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2812 Jim_AppendStrings(interp, Jim_GetResult(interp), "mem2array: cannot read memory", NULL);
2813 e = JIM_ERR;
2814 len = 0;
2815 } else {
2816 v = 0; /* shut up gcc */
2817 for (i = 0 ;i < count ;i++, n++) {
2818 switch (width) {
2819 case 4:
2820 v = target_buffer_get_u32(target, &buffer[i*width]);
2821 break;
2822 case 2:
2823 v = target_buffer_get_u16(target, &buffer[i*width]);
2824 break;
2825 case 1:
2826 v = buffer[i] & 0x0ff;
2827 break;
2828 }
2829 new_int_array_element(interp, varname, n, v);
2830 }
2831 len -= count;
2832 }
2833 }
2834
2835 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2836
2837 return JIM_OK;
2838 }
2839
2840 static int get_int_array_element(Jim_Interp * interp, const char *varname, int idx, u32 *val)
2841 {
2842 char *namebuf;
2843 Jim_Obj *nameObjPtr, *valObjPtr;
2844 int result;
2845 long l;
2846
2847 namebuf = alloc_printf("%s(%d)", varname, idx);
2848 if (!namebuf)
2849 return JIM_ERR;
2850
2851 nameObjPtr = Jim_NewStringObj(interp, namebuf, -1);
2852 if (!nameObjPtr)
2853 {
2854 free(namebuf);
2855 return JIM_ERR;
2856 }
2857
2858 Jim_IncrRefCount(nameObjPtr);
2859 valObjPtr = Jim_GetVariable(interp, nameObjPtr, JIM_ERRMSG);
2860 Jim_DecrRefCount(interp, nameObjPtr);
2861 free(namebuf);
2862 if (valObjPtr == NULL)
2863 return JIM_ERR;
2864
2865 result = Jim_GetLong(interp, valObjPtr, &l);
2866 /* printf("%s(%d) => 0%08x\n", varname, idx, val); */
2867 *val = l;
2868 return result;
2869 }
2870
2871 static int jim_array2mem(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
2872 {
2873 command_context_t *context;
2874 target_t *target;
2875
2876 context = Jim_GetAssocData(interp, "context");
2877 if (context == NULL){
2878 LOG_ERROR("array2mem: no command context");
2879 return JIM_ERR;
2880 }
2881 target = get_current_target(context);
2882 if (target == NULL){
2883 LOG_ERROR("array2mem: no current target");
2884 return JIM_ERR;
2885 }
2886
2887 return target_array2mem( interp,target, argc, argv );
2888 }
2889
2890
2891 static int target_array2mem(Jim_Interp *interp, target_t *target, int argc, Jim_Obj *const *argv)
2892 {
2893 long l;
2894 u32 width;
2895 u32 len;
2896 u32 addr;
2897 u32 count;
2898 u32 v;
2899 const char *varname;
2900 u8 buffer[4096];
2901 int i, n, e, retval;
2902
2903 /* argv[1] = name of array to get the data
2904 * argv[2] = desired width
2905 * argv[3] = memory address
2906 * argv[4] = count to write
2907 */
2908 if (argc != 5) {
2909 Jim_WrongNumArgs(interp, 1, argv, "varname width addr nelems");
2910 return JIM_ERR;
2911 }
2912 varname = Jim_GetString(argv[1], &len);
2913 /* given "foo" get space for worse case "foo(%d)" .. add 20 */
2914
2915 e = Jim_GetLong(interp, argv[2], &l);
2916 width = l;
2917 if (e != JIM_OK) {
2918 return e;
2919 }
2920
2921 e = Jim_GetLong(interp, argv[3], &l);
2922 addr = l;
2923 if (e != JIM_OK) {
2924 return e;
2925 }
2926 e = Jim_GetLong(interp, argv[4], &l);
2927 len = l;
2928 if (e != JIM_OK) {
2929 return e;
2930 }
2931 switch (width) {
2932 case 8:
2933 width = 1;
2934 break;
2935 case 16:
2936 width = 2;
2937 break;
2938 case 32:
2939 width = 4;
2940 break;
2941 default:
2942 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2943 Jim_AppendStrings( interp, Jim_GetResult(interp), "Invalid width param, must be 8/16/32", NULL );
2944 return JIM_ERR;
2945 }
2946 if (len == 0) {
2947 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2948 Jim_AppendStrings(interp, Jim_GetResult(interp), "array2mem: zero width read?", NULL);
2949 return JIM_ERR;
2950 }
2951 if ((addr + (len * width)) < addr) {
2952 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2953 Jim_AppendStrings(interp, Jim_GetResult(interp), "array2mem: addr + len - wraps to zero?", NULL);
2954 return JIM_ERR;
2955 }
2956 /* absurd transfer size? */
2957 if (len > 65536) {
2958 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2959 Jim_AppendStrings(interp, Jim_GetResult(interp), "array2mem: absurd > 64K item request", NULL);
2960 return JIM_ERR;
2961 }
2962
2963 if ((width == 1) ||
2964 ((width == 2) && ((addr & 1) == 0)) ||
2965 ((width == 4) && ((addr & 3) == 0))) {
2966 /* all is well */
2967 } else {
2968 char buf[100];
2969 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
2970 sprintf(buf, "array2mem address: 0x%08x is not aligned for %d byte reads", addr, width);
2971 Jim_AppendStrings(interp, Jim_GetResult(interp), buf , NULL);
2972 return JIM_ERR;
2973 }
2974
2975
2976 /* Transfer loop */
2977
2978 /* index counter */
2979 n = 0;
2980 /* assume ok */
2981 e = JIM_OK;
2982 while (len) {
2983 /* Slurp... in buffer size chunks */
2984
2985 count = len; /* in objects.. */
2986 if (count > (sizeof(buffer)/width)) {
2987 count = (sizeof(buffer)/width);
2988 }
2989
2990 v = 0; /* shut up gcc */
2991 for (i = 0 ;i < count ;i++, n++) {
2992 get_int_array_element(interp, varname, n, &v);
2993 switch (width) {
2994 case 4:
2995 target_buffer_set_u32(target, &buffer[i*width], v);
2996 break;
2997 case 2:
2998 target_buffer_set_u16(target, &buffer[i*width], v);
2999 break;
3000 case 1:
3001 buffer[i] = v & 0x0ff;
3002 break;
3003 }
3004 }
3005 len -= count;
3006
3007 retval = target->type->write_memory(target, addr, width, count, buffer);
3008 if (retval != ERROR_OK) {
3009 /* BOO !*/
3010 LOG_ERROR("array2mem: Write @ 0x%08x, w=%d, cnt=%d, failed", addr, width, count);
3011 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
3012 Jim_AppendStrings(interp, Jim_GetResult(interp), "array2mem: cannot read memory", NULL);
3013 e = JIM_ERR;
3014 len = 0;
3015 }
3016 }
3017
3018 Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
3019
3020 return JIM_OK;
3021 }
3022
3023 void
3024 target_all_handle_event( enum target_event e )
3025 {
3026 target_t *target;
3027
3028
3029 LOG_DEBUG( "**all*targets: event: %d, %s",
3030 e,
3031 Jim_Nvp_value2name_simple( nvp_target_event, e )->name );
3032
3033 target = all_targets;
3034 while (target){
3035 target_handle_event( target, e );
3036 target = target->next;
3037 }
3038 }
3039
3040 void
3041 target_handle_event( target_t *target, enum target_event e )
3042 {
3043 target_event_action_t *teap;
3044 int done;
3045
3046 teap = target->event_action;
3047
3048 done = 0;
3049 while( teap ){
3050 if( teap->event == e ){
3051 done = 1;
3052 LOG_DEBUG( "target: (%d) %s (%s) event: %d (%s) action: %s\n",
3053 target->target_number,
3054 target->cmd_name,
3055 target->type->name,
3056 e,
3057 Jim_Nvp_value2name_simple( nvp_target_event, e )->name,
3058 Jim_GetString( teap->body, NULL ) );
3059 Jim_EvalObj( interp, teap->body );
3060 }
3061 teap = teap->next;
3062 }
3063 if( !done ){
3064 LOG_DEBUG( "event: %d %s - no action",
3065 e,
3066 Jim_Nvp_value2name_simple( nvp_target_event, e )->name );
3067 }
3068 }
3069
3070 enum target_cfg_param {
3071 TCFG_TYPE,
3072 TCFG_EVENT,
3073 TCFG_WORK_AREA_VIRT,
3074 TCFG_WORK_AREA_PHYS,
3075 TCFG_WORK_AREA_SIZE,
3076 TCFG_WORK_AREA_BACKUP,
3077 TCFG_ENDIAN,
3078 TCFG_VARIANT,
3079 TCFG_CHAIN_POSITION,
3080 };
3081
3082
3083 static Jim_Nvp nvp_config_opts[] = {
3084 { .name = "-type", .value = TCFG_TYPE },
3085 { .name = "-event", .value = TCFG_EVENT },
3086 { .name = "-work-area-virt", .value = TCFG_WORK_AREA_VIRT },
3087 { .name = "-work-area-phys", .value = TCFG_WORK_AREA_PHYS },
3088 { .name = "-work-area-size", .value = TCFG_WORK_AREA_SIZE },
3089 { .name = "-work-area-backup", .value = TCFG_WORK_AREA_BACKUP },
3090 { .name = "-endian" , .value = TCFG_ENDIAN },
3091 { .name = "-variant", .value = TCFG_VARIANT },
3092 { .name = "-chain-position", .value = TCFG_CHAIN_POSITION },
3093
3094 { .name = NULL, .value = -1 }
3095 };
3096
3097
3098 static int
3099 target_configure( Jim_GetOptInfo *goi,
3100 target_t *target )
3101 {
3102 Jim_Nvp *n;
3103 Jim_Obj *o;
3104 jim_wide w;
3105 char *cp;
3106 int e;
3107
3108
3109 /* parse config or cget options ... */
3110 while( goi->argc > 0 ){
3111 Jim_SetEmptyResult( goi->interp );
3112 //Jim_GetOpt_Debug( goi );
3113
3114 if( target->type->target_jim_configure ){
3115 /* target defines a configure function */
3116 /* target gets first dibs on parameters */
3117 e = (*(target->type->target_jim_configure))( target, goi );
3118 if( e == JIM_OK ){
3119 /* more? */
3120 continue;
3121 }
3122 if( e == JIM_ERR ){
3123 /* An error */
3124 return e;
3125 }
3126 /* otherwise we 'continue' below */
3127 }
3128 e = Jim_GetOpt_Nvp( goi, nvp_config_opts, &n );
3129 if( e != JIM_OK ){
3130 Jim_GetOpt_NvpUnknown( goi, nvp_config_opts, 0 );
3131 return e;
3132 }
3133 switch( n->value ){
3134 case TCFG_TYPE:
3135 /* not setable */
3136 if( goi->isconfigure ){
3137 Jim_SetResult_sprintf( goi->interp, "not setable: %s", n->name );
3138 return JIM_ERR;
3139 } else {
3140 no_params:
3141 if( goi->argc != 0 ){
3142 Jim_WrongNumArgs( goi->interp, goi->argc, goi->argv, "NO PARAMS");
3143 return JIM_ERR;
3144 }
3145 }
3146 Jim_SetResultString( goi->interp, target->type->name, -1 );
3147 /* loop for more */
3148 break;
3149 case TCFG_EVENT:
3150 if( goi->argc == 0 ){
3151 Jim_WrongNumArgs( goi->interp, goi->argc, goi->argv, "-event ?event-name? ...");
3152 return JIM_ERR;
3153 }
3154
3155 e = Jim_GetOpt_Nvp( goi, nvp_target_event, &n );
3156 if( e != JIM_OK ){
3157 Jim_GetOpt_NvpUnknown( goi, nvp_target_event, 1 );
3158 return e;
3159 }
3160
3161 if( goi->isconfigure ){
3162 if( goi->argc == 0 ){
3163 Jim_WrongNumArgs( goi->interp, goi->argc, goi->argv, "-event ?event-name? ?EVENT-BODY?");
3164 return JIM_ERR;
3165 }
3166 } else {
3167 if( goi->argc != 0 ){
3168 Jim_WrongNumArgs(goi->interp, goi->argc, goi->argv, "-event ?event-name?");
3169 return JIM_ERR;
3170 }
3171 }
3172
3173
3174 {
3175 target_event_action_t *teap;
3176
3177 teap = target->event_action;
3178 /* replace existing? */
3179 while( teap ){
3180 if( teap->event == n->value ){
3181 break;
3182 }
3183 teap = teap->next;
3184 }
3185
3186 if( goi->isconfigure ){
3187 if( teap == NULL ){
3188 /* create new */
3189 teap = calloc( 1, sizeof(*teap) );
3190 }
3191 teap->event = n->value;
3192 Jim_GetOpt_Obj( goi, &o );
3193 if( teap->body ){
3194 Jim_DecrRefCount( interp, teap->body );
3195 }
3196 teap->body = Jim_DuplicateObj( goi->interp, o );
3197 /*
3198 * FIXME:
3199 * Tcl/TK - "tk events" have a nice feature.
3200 * See the "BIND" command.
3201 * We should support that here.
3202 * You can specify %X and %Y in the event code.
3203 * The idea is: %T - target name.
3204 * The idea is: %N - target number
3205 * The idea is: %E - event name.
3206 */
3207 Jim_IncrRefCount( teap->body );
3208
3209 /* add to head of event list */
3210 teap->next = target->event_action;
3211 target->event_action = teap;
3212 Jim_SetEmptyResult(goi->interp);
3213 } else {
3214 /* get */
3215 if( teap == NULL ){
3216 Jim_SetEmptyResult( goi->interp );
3217 } else {
3218 Jim_SetResult( goi->interp, Jim_DuplicateObj( goi->interp, teap->body ) );
3219 }
3220 }
3221 }
3222 /* loop for more */
3223 break;
3224
3225 case TCFG_WORK_AREA_VIRT:
3226 if( goi->isconfigure ){
3227 target_free_all_working_areas(target);
3228 e = Jim_GetOpt_Wide( goi, &w );
3229 if( e != JIM_OK ){
3230 return e;
3231 }
3232 target->working_area_virt = w;
3233 } else {
3234 if( goi->argc != 0 ){
3235 goto no_params;
3236 }
3237 }
3238 Jim_SetResult( interp, Jim_NewIntObj( goi->interp, target->working_area_virt ) );
3239 /* loop for more */
3240 break;
3241
3242 case TCFG_WORK_AREA_PHYS:
3243 if( goi->isconfigure ){
3244 target_free_all_working_areas(target);
3245 e = Jim_GetOpt_Wide( goi, &w );
3246 if( e != JIM_OK ){
3247 return e;
3248 }
3249 target->working_area_phys = w;
3250 } else {
3251 if( goi->argc != 0 ){
3252 goto no_params;
3253 }
3254 }
3255 Jim_SetResult( interp, Jim_NewIntObj( goi->interp, target->working_area_phys ) );
3256 /* loop for more */
3257 break;
3258
3259 case TCFG_WORK_AREA_SIZE:
3260 if( goi->isconfigure ){
3261 target_free_all_working_areas(target);
3262 e = Jim_GetOpt_Wide( goi, &w );
3263 if( e != JIM_OK ){
3264 return e;
3265 }
3266 target->working_area_size = w;
3267 } else {
3268 if( goi->argc != 0 ){
3269 goto no_params;
3270 }
3271 }
3272 Jim_SetResult( interp, Jim_NewIntObj( goi->interp, target->working_area_size ) );
3273 /* loop for more */
3274 break;
3275
3276 case TCFG_WORK_AREA_BACKUP:
3277 if( goi->isconfigure ){
3278 target_free_all_working_areas(target);
3279 e = Jim_GetOpt_Wide( goi, &w );
3280 if( e != JIM_OK ){
3281 return e;
3282 }
3283 /* make this exactly 1 or 0 */
3284 target->backup_working_area = (!!w);
3285 } else {
3286 if( goi->argc != 0 ){
3287 goto no_params;
3288 }
3289 }
3290 Jim_SetResult( interp, Jim_NewIntObj( goi->interp, target->working_area_size ) );
3291 /* loop for more e*/
3292 break;
3293
3294 case TCFG_ENDIAN:
3295 if( goi->isconfigure ){
3296 e = Jim_GetOpt_Nvp( goi, nvp_target_endian, &n );
3297 if( e != JIM_OK ){
3298 Jim_GetOpt_NvpUnknown( goi, nvp_target_endian, 1 );
3299 return e;
3300 }
3301 target->endianness = n->value;
3302 } else {
3303 if( goi->argc != 0 ){
3304 goto no_params;
3305 }
3306 }
3307 n = Jim_Nvp_value2name_simple( nvp_target_endian, target->endianness );
3308 if( n->name == NULL ){
3309 target->endianness = TARGET_LITTLE_ENDIAN;
3310 n = Jim_Nvp_value2name_simple( nvp_target_endian, target->endianness );
3311 }
3312 Jim_SetResultString( goi->interp, n->name, -1 );
3313 /* loop for more */
3314 break;
3315
3316 case TCFG_VARIANT:
3317 if( goi->isconfigure ){
3318 if( goi->argc < 1 ){
3319 Jim_SetResult_sprintf( goi->interp,
3320 "%s ?STRING?",
3321 n->name );
3322 return JIM_ERR;
3323 }
3324 if( target->variant ){
3325 free((void *)(target->variant));
3326 }
3327 e = Jim_GetOpt_String( goi, &cp, NULL );
3328 target->variant = strdup(cp);
3329 } else {
3330 if( goi->argc != 0 ){
3331 goto no_params;
3332 }
3333 }
3334 Jim_SetResultString( goi->interp, target->variant,-1 );
3335 /* loop for more */
3336 break;
3337 case TCFG_CHAIN_POSITION:
3338 if( goi->isconfigure ){
3339 target_free_all_working_areas(target);
3340 e = Jim_GetOpt_Wide( goi, &w );
3341 if( e != JIM_OK ){
3342 return e;
3343 }
3344 /* make this exactly 1 or 0 */
3345 target->chain_position = w;
3346 } else {
3347 if( goi->argc != 0 ){
3348 goto no_params;
3349 }
3350 }
3351 Jim_SetResult( interp, Jim_NewIntObj( goi->interp, target->chain_position ) );
3352 /* loop for more e*/
3353 break;
3354 }
3355 } /* while( goi->argc ) */
3356 /* done - we return */
3357 return JIM_OK;
3358 }
3359
3360
3361 /** this is the 'tcl' handler for the target specific command */
3362 static int
3363 tcl_target_func( Jim_Interp *interp,
3364 int argc,
3365 Jim_Obj *const *argv )
3366 {
3367 Jim_GetOptInfo goi;
3368 jim_wide a,b,c;
3369 int x,y,z;
3370 u8 target_buf[32];
3371 Jim_Nvp *n;
3372 target_t *target;
3373 struct command_context_s *cmd_ctx;
3374 int e;
3375
3376
3377 enum {
3378 TS_CMD_CONFIGURE,
3379 TS_CMD_CGET,
3380
3381 TS_CMD_MWW, TS_CMD_MWH, TS_CMD_MWB,
3382 TS_CMD_MDW, TS_CMD_MDH, TS_CMD_MDB,
3383 TS_CMD_MRW, TS_CMD_MRH, TS_CMD_MRB,
3384 TS_CMD_MEM2ARRAY, TS_CMD_ARRAY2MEM,
3385 TS_CMD_EXAMINE,
3386 TS_CMD_POLL,
3387 TS_CMD_RESET,
3388 TS_CMD_HALT,
3389 TS_CMD_WAITSTATE,
3390 TS_CMD_EVENTLIST,
3391 TS_CMD_CURSTATE,
3392 TS_CMD_INVOKE_EVENT,
3393 };
3394
3395 static const Jim_Nvp target_options[] = {
3396 { .name = "configure", .value = TS_CMD_CONFIGURE },
3397 { .name = "cget", .value = TS_CMD_CGET },
3398 { .name = "mww", .value = TS_CMD_MWW },
3399 { .name = "mwh", .value = TS_CMD_MWH },
3400 { .name = "mwb", .value = TS_CMD_MWB },
3401 { .name = "mdw", .value = TS_CMD_MDW },
3402 { .name = "mdh", .value = TS_CMD_MDH },
3403 { .name = "mdb", .value = TS_CMD_MDB },
3404 { .name = "mem2array", .value = TS_CMD_MEM2ARRAY },
3405 { .name = "array2mem", .value = TS_CMD_ARRAY2MEM },
3406 { .name = "eventlist", .value = TS_CMD_EVENTLIST },
3407 { .name = "curstate", .value = TS_CMD_CURSTATE },
3408
3409 { .name = "arp_examine", .value = TS_CMD_EXAMINE },
3410 { .name = "arp_poll", .value = TS_CMD_POLL },
3411 { .name = "arp_reset", .value = TS_CMD_RESET },
3412 { .name = "arp_halt", .value = TS_CMD_HALT },
3413 { .name = "arp_waitstate", .value = TS_CMD_WAITSTATE },
3414 { .name = "invoke-event", .value = TS_CMD_INVOKE_EVENT },
3415
3416 { .name = NULL, .value = -1 },
3417 };
3418
3419
3420 /* go past the "command" */
3421 Jim_GetOpt_Setup( &goi, interp, argc-1, argv+1 );
3422
3423 target = Jim_CmdPrivData( goi.interp );
3424 cmd_ctx = Jim_GetAssocData(goi.interp, "context");
3425
3426 /* commands here are in an NVP table */
3427 e = Jim_GetOpt_Nvp( &goi, target_options, &n );
3428 if( e != JIM_OK ){
3429 Jim_GetOpt_NvpUnknown( &goi, target_options, 0 );
3430 return e;
3431 }
3432 // Assume blank result
3433 Jim_SetEmptyResult( goi.interp );
3434
3435 switch( n->value ){
3436 case TS_CMD_CONFIGURE:
3437 if( goi.argc < 2 ){
3438 Jim_WrongNumArgs( goi.interp, goi.argc, goi.argv, "missing: -option VALUE ...");
3439 return JIM_ERR;
3440 }
3441 goi.isconfigure = 1;
3442 return target_configure( &goi, target );
3443 case TS_CMD_CGET:
3444 // some things take params
3445 if( goi.argc < 1 ){
3446 Jim_WrongNumArgs( goi.interp, 0, goi.argv, "missing: ?-option?");
3447 return JIM_ERR;
3448 }
3449 goi.isconfigure = 0;
3450 return target_configure( &goi, target );
3451 break;
3452 case TS_CMD_MWW:
3453 case TS_CMD_MWH:
3454 case TS_CMD_MWB:
3455 /* argv[0] = cmd
3456 * argv[1] = address
3457 * argv[2] = data
3458 * argv[3] = optional count.
3459 */
3460
3461 if( (goi.argc == 3) || (goi.argc == 4) ){
3462 /* all is well */
3463 } else {
3464 mwx_error:
3465 Jim_SetResult_sprintf( goi.interp, "expected: %s ADDR DATA [COUNT]", n->name );
3466 return JIM_ERR;
3467 }
3468
3469 e = Jim_GetOpt_Wide( &goi, &a );
3470 if( e != JIM_OK ){
3471 goto mwx_error;
3472 }
3473
3474 e = Jim_GetOpt_Wide( &goi, &b );
3475 if( e != JIM_OK ){
3476 goto mwx_error;
3477 }
3478 if( goi.argc ){
3479 e = Jim_GetOpt_Wide( &goi, &c );
3480 if( e != JIM_OK ){
3481 goto mwx_error;
3482 }
3483 } else {
3484 c = 1;
3485 }
3486
3487 switch( n->value ){
3488 case TS_CMD_MWW:
3489 target_buffer_set_u32( target, target_buf, b );
3490 b = 4;
3491 break;
3492 case TS_CMD_MWH:
3493 target_buffer_set_u16( target, target_buf, b );
3494 b = 2;
3495 break;
3496 case TS_CMD_MWB:
3497 target_buffer_set_u8( target, target_buf, b );
3498 b = 1;
3499 break;
3500 }
3501 for( x = 0 ; x < c ; x++ ){
3502 e = target->type->write_memory( target, a, b, 1, target_buf );
3503 if( e != ERROR_OK ){
3504 Jim_SetResult_sprintf( interp, "Error writing @ 0x%08x: %d\n", (int)(a), e );
3505 return JIM_ERR;
3506 }
3507 /* b = width */
3508 a = a + b;
3509 }
3510 return JIM_OK;
3511 break;
3512
3513 /* display */
3514 case TS_CMD_MDW:
3515 case TS_CMD_MDH:
3516 case TS_CMD_MDB:
3517 /* argv[0] = command
3518 * argv[1] = address
3519 * argv[2] = optional count
3520 */
3521 if( (goi.argc == 2) || (goi.argc == 3) ){
3522 Jim_SetResult_sprintf( goi.interp, "expected: %s ADDR [COUNT]", n->name );
3523 return JIM_ERR;
3524 }
3525 e = Jim_GetOpt_Wide( &goi, &a );
3526 if( e != JIM_OK ){
3527 return JIM_ERR;
3528 }
3529 if( goi.argc ){
3530 e = Jim_GetOpt_Wide( &goi, &c );
3531 if( e != JIM_OK ){
3532 return JIM_ERR;
3533 }
3534 } else {
3535 c = 1;
3536 }
3537 b = 1; /* shut up gcc */
3538 switch( n->value ){
3539 case TS_CMD_MDW:
3540 b = 4;
3541 break;
3542 case TS_CMD_MDH:
3543 b = 2;
3544 break;
3545 case TS_CMD_MDB:
3546 b = 1;
3547 break;
3548 }
3549
3550 /* convert to "bytes" */
3551 c = c * b;
3552 /* count is now in 'BYTES' */
3553 while( c > 0 ){
3554 y = c;
3555 if( y > 16 ){
3556 y = 16;
3557 }
3558 e = target->type->read_memory( target, a, b, y / b, target_buf );
3559 if( e != ERROR_OK ){
3560 Jim_SetResult_sprintf( interp, "error reading target @ 0x%08lx", (int)(a) );
3561 return JIM_ERR;
3562 }
3563
3564 Jim_fprintf( interp, interp->cookie_stdout, "0x%08x ", (int)(a) );
3565 switch( b ){
3566 case 4:
3567 for( x = 0 ; (x < 16) && (x < y) ; x += 4 ){
3568 z = target_buffer_get_u32( target, &(target_buf[ x * 4 ]) );
3569 Jim_fprintf( interp, interp->cookie_stdout, "%08x ", (int)(z) );
3570 }
3571 for( ; (x < 16) ; x += 4 ){
3572 Jim_fprintf( interp, interp->cookie_stdout, " " );
3573 }
3574 break;
3575 case 2:
3576 for( x = 0 ; (x < 16) && (x < y) ; x += 2 ){
3577 z = target_buffer_get_u16( target, &(target_buf[ x * 2 ]) );
3578 Jim_fprintf( interp, interp->cookie_stdout, "%04x ", (int)(z) );
3579 }
3580 for( ; (x < 16) ; x += 2 ){
3581 Jim_fprintf( interp, interp->cookie_stdout, " " );
3582 }
3583 break;
3584 case 1:
3585 default:
3586 for( x = 0 ; (x < 16) && (x < y) ; x += 1 ){
3587 z = target_buffer_get_u8( target, &(target_buf[ x * 4 ]) );
3588 Jim_fprintf( interp, interp->cookie_stdout, "%02x ", (int)(z) );
3589 }
3590 for( ; (x < 16) ; x += 1 ){
3591 Jim_fprintf( interp, interp->cookie_stdout, " " );
3592 }
3593 break;
3594 }
3595 /* ascii-ify the bytes */
3596 for( x = 0 ; x < y ; x++ ){
3597 if( (target_buf[x] >= 0x20) &&
3598 (target_buf[x] <= 0x7e) ){
3599 /* good */
3600 } else {
3601 /* smack it */
3602 target_buf[x] = '.';
3603 }
3604 }
3605 /* space pad */
3606 while( x < 16 ){
3607 target_buf[x] = ' ';
3608 x++;
3609 }
3610 /* terminate */
3611 target_buf[16] = 0;
3612 /* print - with a newline */
3613 Jim_fprintf( interp, interp->cookie_stdout, "%s\n", target_buf );
3614 /* NEXT... */
3615 c -= 16;
3616 a += 16;
3617 }
3618 return JIM_OK;
3619 case TS_CMD_MEM2ARRAY:
3620 return target_mem2array( goi.interp, target, goi.argc, goi.argv );
3621 break;
3622 case TS_CMD_ARRAY2MEM:
3623 return target_array2mem( goi.interp, target, goi.argc, goi.argv );
3624 break;
3625 case TS_CMD_EXAMINE:
3626 if( goi.argc ){
3627 Jim_WrongNumArgs( goi.interp, 2, argv, "[no parameters]");
3628 return JIM_ERR;
3629 }
3630 e = target->type->examine( target );
3631 if( e != ERROR_OK ){
3632 Jim_SetResult_sprintf( interp, "examine-fails: %d", e );
3633 return JIM_ERR;
3634 }
3635 return JIM_OK;
3636 case TS_CMD_POLL:
3637 if( goi.argc ){
3638 Jim_WrongNumArgs( goi.interp, 2, argv, "[no parameters]");
3639 return JIM_ERR;
3640 }
3641 if( !(target->type->examined) ){
3642 e = ERROR_TARGET_NOT_EXAMINED;
3643 } else {
3644 e = target->type->poll( target );
3645 }
3646 if( e != ERROR_OK ){
3647 Jim_SetResult_sprintf( interp, "poll-fails: %d", e );
3648 return JIM_ERR;
3649 } else {
3650 return JIM_OK;
3651 }
3652 break;
3653 case TS_CMD_RESET:
3654 if( goi.argc != 2 ){
3655 Jim_WrongNumArgs( interp, 2, argv, "t|f|assert|deassert BOOL");
3656 return JIM_ERR;
3657 }
3658 e = Jim_GetOpt_Nvp( &goi, nvp_assert, &n );
3659 if( e != JIM_OK ){
3660 Jim_GetOpt_NvpUnknown( &goi, nvp_assert, 1 );
3661 return e;
3662 }
3663 // the halt or not param
3664 e = Jim_GetOpt_Wide( &goi, &a);
3665 if( e != JIM_OK ){
3666 return e;
3667 }
3668 // determine if we should halt or not.
3669 target->reset_halt = !!a;
3670 // When this happens - all workareas are invalid.
3671 target_free_all_working_areas_restore(target, 0);
3672
3673 // do the assert
3674 if( n->value == NVP_ASSERT ){
3675 target->type->assert_reset( target );
3676 } else {
3677 target->type->deassert_reset( target );
3678 }
3679 return JIM_OK;
3680 case TS_CMD_HALT:
3681 if( goi.argc ){
3682 Jim_WrongNumArgs( goi.interp, 0, argv, "halt [no parameters]");
3683 return JIM_ERR;
3684 }
3685 target->type->halt( target );
3686 return JIM_OK;
3687 case TS_CMD_WAITSTATE:
3688 // params: <name> statename timeoutmsecs
3689 if( goi.argc != 2 ){
3690 Jim_SetResult_sprintf( goi.interp, "%s STATENAME TIMEOUTMSECS", n->name );
3691 return JIM_ERR;
3692 }
3693 e = Jim_GetOpt_Nvp( &goi, nvp_target_state, &n );
3694 if( e != JIM_OK ){
3695 Jim_GetOpt_NvpUnknown( &goi, nvp_target_state,1 );
3696 return e;
3697 }
3698 e = Jim_GetOpt_Wide( &goi, &a );
3699 if( e != JIM_OK ){
3700 return e;
3701 }
3702 e = target_wait_state( target, n->value, a );
3703 if( e != ERROR_OK ){
3704 Jim_SetResult_sprintf( goi.interp,
3705 "target: %s wait %s fails (%d) %s",
3706 target->cmd_name,
3707 n->name,
3708 e, target_strerror_safe(e) );
3709 return JIM_ERR;
3710 } else {
3711 return JIM_OK;
3712 }
3713 case TS_CMD_EVENTLIST:
3714 /* List for human, Events defined for this target.
3715 * scripts/programs should use 'name cget -event NAME'
3716 */
3717 {
3718 target_event_action_t *teap;
3719 teap = target->event_action;
3720 command_print( cmd_ctx, "Event actions for target (%d) %s\n",
3721 target->target_number,
3722 target->cmd_name );
3723 command_print( cmd_ctx, "%-25s | Body", "Event");
3724 command_print( cmd_ctx, "------------------------- | ----------------------------------------");
3725 while( teap ){
3726 command_print( cmd_ctx,
3727 "%-25s | %s",
3728 Jim_Nvp_value2name_simple( nvp_target_event, teap->event )->name,
3729 Jim_GetString( teap->body, NULL ) );
3730 teap = teap->next;
3731 }
3732 command_print( cmd_ctx, "***END***");
3733 return JIM_OK;
3734 }
3735 case TS_CMD_CURSTATE:
3736 if( goi.argc != 0 ){
3737 Jim_WrongNumArgs( goi.interp, 0, argv, "[no parameters]");
3738 return JIM_ERR;
3739 }
3740 Jim_SetResultString( goi.interp,
3741 Jim_Nvp_value2name_simple(nvp_target_state,target->state)->name,-1);
3742 return JIM_OK;
3743 case TS_CMD_INVOKE_EVENT:
3744 if( goi.argc != 1 ){
3745 Jim_SetResult_sprintf( goi.interp, "%s ?EVENTNAME?",n->name);
3746 return JIM_ERR;
3747 }
3748 e = Jim_GetOpt_Nvp( &goi, nvp_target_event, &n );
3749 if( e != JIM_OK ){
3750 Jim_GetOpt_NvpUnknown( &goi, nvp_target_event, 1 );
3751 return e;
3752 }
3753 target_handle_event( target, n->value );
3754 return JIM_OK;
3755 }
3756 return JIM_ERR;
3757 }
3758
3759
3760 static int
3761 target_create( Jim_GetOptInfo *goi )
3762 {
3763
3764 Jim_Obj *new_cmd;
3765 Jim_Cmd *cmd;
3766 const char *cp;
3767 char *cp2;
3768 int e;
3769 int x;
3770 target_t *target;
3771 struct command_context_s *cmd_ctx;
3772
3773 cmd_ctx = Jim_GetAssocData(goi->interp, "context");
3774 if( goi->argc < 3 ){
3775 Jim_WrongNumArgs( goi->interp, 1, goi->argv, "?name? ?type? ..options...");
3776 return JIM_ERR;
3777 }
3778
3779 /* COMMAND */
3780 Jim_GetOpt_Obj( goi, &new_cmd );
3781 /* does this command exist? */
3782 cmd = Jim_GetCommand( goi->interp, new_cmd, JIM_ERRMSG );
3783 if( cmd ){
3784 cp = Jim_GetString( new_cmd, NULL );
3785 Jim_SetResult_sprintf(goi->interp, "Command/target: %s Exists", cp);
3786 return JIM_ERR;
3787 }
3788
3789 /* TYPE */
3790 e = Jim_GetOpt_String( goi, &cp2, NULL );
3791 cp = cp2;
3792 /* now does target type exist */
3793 for( x = 0 ; target_types[x] ; x++ ){
3794 if( 0 == strcmp( cp, target_types[x]->name ) ){
3795 /* found */
3796 break;
3797 }
3798 }
3799 if( target_types[x] == NULL ){
3800 Jim_SetResult_sprintf( goi->interp, "Unknown target type %s, try one of ", cp );
3801 for( x = 0 ; target_types[x] ; x++ ){
3802 if( target_types[x+1] ){
3803 Jim_AppendStrings( goi->interp,
3804 Jim_GetResult(goi->interp),
3805 target_types[x]->name,
3806 ", ", NULL);
3807 } else {
3808 Jim_AppendStrings( goi->interp,
3809 Jim_GetResult(goi->interp),
3810 " or ",
3811 target_types[x]->name,NULL );
3812 }
3813 }
3814 return JIM_ERR;
3815 }
3816
3817
3818 /* Create it */
3819 target = calloc(1,sizeof(target_t));
3820 /* set target number */
3821 target->target_number = new_target_number();
3822
3823 /* allocate memory for each unique target type */
3824 target->type = (target_type_t*)calloc(1,sizeof(target_type_t));
3825
3826 memcpy( target->type, target_types[x], sizeof(target_type_t));
3827
3828 /* will be set by "-endian" */
3829 target->endianness = TARGET_ENDIAN_UNKNOWN;
3830
3831 target->working_area = 0x0;
3832 target->working_area_size = 0x0;
3833 target->working_areas = NULL;
3834 target->backup_working_area = 0;
3835
3836 target->state = TARGET_UNKNOWN;
3837 target->debug_reason = DBG_REASON_UNDEFINED;
3838 target->reg_cache = NULL;
3839 target->breakpoints = NULL;
3840 target->watchpoints = NULL;
3841 target->next = NULL;
3842 target->arch_info = NULL;
3843
3844 /* initialize trace information */
3845 target->trace_info = malloc(sizeof(trace_t));
3846 target->trace_info->num_trace_points = 0;
3847 target->trace_info->trace_points_size = 0;
3848 target->trace_info->trace_points = NULL;
3849 target->trace_info->trace_history_size = 0;
3850 target->trace_info->trace_history = NULL;
3851 target->trace_info->trace_history_pos = 0;
3852 target->trace_info->trace_history_overflowed = 0;
3853
3854 target->dbgmsg = NULL;
3855 target->dbg_msg_enabled = 0;
3856
3857 target->endianness = TARGET_ENDIAN_UNKNOWN;
3858
3859 /* Do the rest as "configure" options */
3860 goi->isconfigure = 1;
3861 e = target_configure( goi, target);
3862 if( e != JIM_OK ){
3863 free( target->type );
3864 free( target );
3865 return e;
3866 }
3867
3868 if( target->endianness == TARGET_ENDIAN_UNKNOWN ){
3869 /* default endian to little if not specified */
3870 target->endianness = TARGET_LITTLE_ENDIAN;
3871 }
3872
3873 /* create the target specific commands */
3874 if( target->type->register_commands ){
3875 (*(target->type->register_commands))( cmd_ctx );
3876 }
3877 if( target->type->target_create ){
3878 (*(target->type->target_create))( target, goi->interp );
3879 }
3880
3881 /* append to end of list */
3882 {
3883 target_t **tpp;
3884 tpp = &(all_targets);
3885 while( *tpp ){
3886 tpp = &( (*tpp)->next );
3887 }
3888 *tpp = target;
3889 }
3890
3891 cp = Jim_GetString( new_cmd, NULL );
3892 target->cmd_name = strdup(cp);
3893
3894 /* now - create the new target name command */
3895 e = Jim_CreateCommand( goi->interp,
3896 /* name */
3897 cp,
3898 tcl_target_func, /* C function */
3899 target, /* private data */
3900 NULL ); /* no del proc */
3901
3902 (*(target->type->target_create))( target, goi->interp );
3903 return e;
3904 }
3905
3906 static int
3907 jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
3908 {
3909 int x,r,e;
3910 jim_wide w;
3911 struct command_context_s *cmd_ctx;
3912 const char *cp;
3913 target_t *target;
3914 Jim_GetOptInfo goi;
3915 enum tcmd {
3916 /* TG = target generic */
3917 TG_CMD_CREATE,
3918 TG_CMD_TYPES,
3919 TG_CMD_NAMES,
3920 TG_CMD_CURRENT,
3921 TG_CMD_NUMBER,
3922 TG_CMD_COUNT,
3923 };
3924 const char *target_cmds[] = {
3925 "create", "types", "names", "current", "number",
3926 "count",
3927 NULL // terminate
3928 };
3929
3930 LOG_DEBUG("Target command params:");
3931 LOG_DEBUG(Jim_Debug_ArgvString( interp, argc, argv) );
3932
3933 cmd_ctx = Jim_GetAssocData( interp, "context" );
3934
3935 Jim_GetOpt_Setup( &goi, interp, argc-1, argv+1 );
3936
3937 if( goi.argc == 0 ){
3938 Jim_WrongNumArgs(interp, 1, argv, "missing: command ...");
3939 return JIM_ERR;
3940 }
3941
3942 /* is this old syntax? */
3943 /* To determine: We have to peek at argv[0]*/
3944 cp = Jim_GetString( goi.argv[0], NULL );
3945 for( x = 0 ; target_types[x] ; x++ ){
3946 if( 0 == strcmp(cp,target_types[x]->name) ){
3947 break;
3948 }
3949 }
3950 if( target_types[x] ){
3951 /* YES IT IS OLD SYNTAX */
3952 Jim_Obj *new_argv[10];
3953 int new_argc;
3954
3955 /* target_old_syntax
3956 *
3957 * argv[0] typename (above)
3958 * argv[1] endian
3959 * argv[2] reset method, deprecated/ignored
3960 * argv[3] = old param
3961 * argv[4] = old param
3962 *
3963 * We will combine all "old params" into a single param.
3964 * Then later, split them again.
3965 */
3966 if( argc < 4 ){
3967 Jim_WrongNumArgs( interp, 1, argv, "[OLDSYNTAX] ?TYPE? ?ENDIAN? ?RESET? ?old-params?");
3968 return JIM_ERR;
3969 }
3970 /* the command */
3971 new_argv[0] = argv[0];
3972 new_argv[1] = Jim_NewStringObj( interp, "create", -1 );
3973 {
3974 char buf[ 30 ];
3975 sprintf( buf, "target%d", new_target_number() );
3976 new_argv[2] = Jim_NewStringObj( interp, buf , -1 );
3977 }
3978 new_argv[3] = goi.argv[0]; /* typename */
3979 new_argv[4] = Jim_NewStringObj( interp, "-endian", -1 );
3980 new_argv[5] = goi.argv[1];
3981 new_argv[6] = Jim_NewStringObj( interp, "-chain-position", -1 );
3982 new_argv[7] = goi.argv[2];
3983 new_argv[8] = Jim_NewStringObj( interp, "-variant", -1 );
3984 new_argv[9] = goi.argv[3];
3985 new_argc = 10;
3986 /*
3987 * new arg syntax:
3988 * argv[0] = command
3989 * argv[1] = create
3990 * argv[2] = cmdname
3991 * argv[3] = typename
3992 * argv[4] = **FIRST** "configure" option.
3993 *
3994 * Here, we make them:
3995 *
3996 * argv[4] = -endian
3997 * argv[5] = little
3998 * argv[6] = -position
3999 * argv[7] = NUMBER
4000 * argv[8] = -variant
4001 * argv[9] = "somestring"
4002 */
4003
4004 /* don't let these be released */
4005 for( x = 0 ; x < new_argc ; x++ ){
4006 Jim_IncrRefCount( new_argv[x]);
4007 }
4008 /* call our self */
4009 LOG_DEBUG("Target OLD SYNTAX - converted to new syntax");
4010
4011 r = jim_target( goi.interp, new_argc, new_argv );
4012
4013 /* release? these items */
4014 for( x = 0 ; x < new_argc ; x++ ){
4015 Jim_DecrRefCount( interp, new_argv[x] );
4016 }
4017 return r;
4018 }
4019
4020 //Jim_GetOpt_Debug( &goi );
4021 r = Jim_GetOpt_Enum( &goi, target_cmds, &x );
4022 if( r != JIM_OK ){
4023 return r;
4024 }
4025
4026 switch(x){
4027 default:
4028 Jim_Panic(goi.interp,"Why am I here?");
4029 return JIM_ERR;
4030 case TG_CMD_CURRENT:
4031 if( goi.argc != 0 ){
4032 Jim_WrongNumArgs( goi.interp, 1, goi.argv, "Too many parameters");
4033 return JIM_ERR;
4034 }
4035 Jim_SetResultString( goi.interp, get_current_target( cmd_ctx )->cmd_name, -1 );
4036 return JIM_OK;
4037 case TG_CMD_TYPES:
4038 if( goi.argc != 0 ){
4039 Jim_WrongNumArgs( goi.interp, 1, goi.argv, "Too many parameters" );
4040 return JIM_ERR;
4041 }
4042 Jim_SetResult( goi.interp, Jim_NewListObj( goi.interp, NULL, 0 ) );
4043 for( x = 0 ; target_types[x] ; x++ ){
4044 Jim_ListAppendElement( goi.interp,
4045 Jim_GetResult(goi.interp),
4046 Jim_NewStringObj( goi.interp, target_types[x]->name, -1 ) );
4047 }
4048 return JIM_OK;
4049 case TG_CMD_NAMES:
4050 if( goi.argc != 0 ){
4051 Jim_WrongNumArgs( goi.interp, 1, goi.argv, "Too many parameters" );
4052 return JIM_ERR;
4053 }
4054 Jim_SetResult( goi.interp, Jim_NewListObj( goi.interp, NULL, 0 ) );
4055 target = all_targets;
4056 while( target ){
4057 Jim_ListAppendElement( goi.interp,
4058 Jim_GetResult(goi.interp),
4059 Jim_NewStringObj( goi.interp, target->cmd_name, -1 ) );
4060 target = target->next;
4061 }
4062 return JIM_OK;
4063 case TG_CMD_CREATE:
4064 if( goi.argc < 3 ){
4065 Jim_WrongNumArgs( goi.interp, goi.argc, goi.argv, "?name ... config options ...");
4066 return JIM_ERR;
4067 }
4068 return target_create( &goi );
4069 break;
4070 case TG_CMD_NUMBER:
4071 if( goi.argc != 1 ){
4072 Jim_SetResult_sprintf( goi.interp, "expected: target number ?NUMBER?");
4073 return JIM_ERR;
4074 }
4075 e = Jim_GetOpt_Wide( &goi, &w );
4076 if( e != JIM_OK ){
4077 return JIM_ERR;
4078 }
4079 {
4080 target_t *t;
4081 t = get_target_by_num(w);
4082 if( t == NULL ){
4083 Jim_SetResult_sprintf( goi.interp,"Target: number %d does not exist", (int)(w));
4084 return JIM_ERR;
4085 }
4086 Jim_SetResultString( goi.interp, t->cmd_name, -1 );
4087 return JIM_OK;
4088 }
4089 case TG_CMD_COUNT:
4090 if( goi.argc != 0 ){
4091 Jim_WrongNumArgs( goi.interp, 0, goi.argv, "<no parameters>");
4092 return JIM_ERR;
4093 }
4094 Jim_SetResult( goi.interp,
4095 Jim_NewIntObj( goi.interp, max_target_number()));
4096 return JIM_OK;
4097 }
4098
4099 return JIM_ERR;
4100 }

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)