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