- fix incorrect svn props from last commit
[openocd.git] / src / target / xscale.c
1 /***************************************************************************
2 * Copyright (C) 2006, 2007 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
29 #include "xscale.h"
30
31 #include "arm7_9_common.h"
32 #include "register.h"
33 #include "target.h"
34 #include "armv4_5.h"
35 #include "arm_simulator.h"
36 #include "arm_disassembler.h"
37 #include "log.h"
38 #include "jtag.h"
39 #include "binarybuffer.h"
40 #include "time_support.h"
41 #include "breakpoints.h"
42 #include "fileio.h"
43
44 #include <stdlib.h>
45 #include <string.h>
46
47 #include <sys/types.h>
48 #include <unistd.h>
49 #include <errno.h>
50
51
52 /* cli handling */
53 int xscale_register_commands(struct command_context_s *cmd_ctx);
54
55 /* forward declarations */
56 int xscale_target_create(struct target_s *target, Jim_Interp *interp);
57 int xscale_init_target(struct command_context_s *cmd_ctx, struct target_s *target);
58 int xscale_quit(void);
59
60 int xscale_arch_state(struct target_s *target);
61 int xscale_poll(target_t *target);
62 int xscale_halt(target_t *target);
63 int xscale_resume(struct target_s *target, int current, u32 address, int handle_breakpoints, int debug_execution);
64 int xscale_step(struct target_s *target, int current, u32 address, int handle_breakpoints);
65 int xscale_debug_entry(target_t *target);
66 int xscale_restore_context(target_t *target);
67
68 int xscale_assert_reset(target_t *target);
69 int xscale_deassert_reset(target_t *target);
70 int xscale_soft_reset_halt(struct target_s *target);
71
72 int xscale_set_reg_u32(reg_t *reg, u32 value);
73
74 int xscale_read_core_reg(struct target_s *target, int num, enum armv4_5_mode mode);
75 int xscale_write_core_reg(struct target_s *target, int num, enum armv4_5_mode mode, u32 value);
76
77 int xscale_read_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer);
78 int xscale_write_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer);
79 int xscale_bulk_write_memory(target_t *target, u32 address, u32 count, u8 *buffer);
80
81 int xscale_add_breakpoint(struct target_s *target, breakpoint_t *breakpoint);
82 int xscale_remove_breakpoint(struct target_s *target, breakpoint_t *breakpoint);
83 int xscale_set_breakpoint(struct target_s *target, breakpoint_t *breakpoint);
84 int xscale_unset_breakpoint(struct target_s *target, breakpoint_t *breakpoint);
85 int xscale_add_watchpoint(struct target_s *target, watchpoint_t *watchpoint);
86 int xscale_remove_watchpoint(struct target_s *target, watchpoint_t *watchpoint);
87 void xscale_enable_watchpoints(struct target_s *target);
88 void xscale_enable_breakpoints(struct target_s *target);
89 static int xscale_virt2phys(struct target_s *target, u32 virtual, u32 *physical);
90 static int xscale_mmu(struct target_s *target, int *enabled);
91
92 int xscale_read_trace(target_t *target);
93
94 target_type_t xscale_target =
95 {
96 .name = "xscale",
97
98 .poll = xscale_poll,
99 .arch_state = xscale_arch_state,
100
101 .target_request_data = NULL,
102
103 .halt = xscale_halt,
104 .resume = xscale_resume,
105 .step = xscale_step,
106
107 .assert_reset = xscale_assert_reset,
108 .deassert_reset = xscale_deassert_reset,
109 .soft_reset_halt = xscale_soft_reset_halt,
110
111 .get_gdb_reg_list = armv4_5_get_gdb_reg_list,
112
113 .read_memory = xscale_read_memory,
114 .write_memory = xscale_write_memory,
115 .bulk_write_memory = xscale_bulk_write_memory,
116 .checksum_memory = arm7_9_checksum_memory,
117 .blank_check_memory = arm7_9_blank_check_memory,
118
119 .run_algorithm = armv4_5_run_algorithm,
120
121 .add_breakpoint = xscale_add_breakpoint,
122 .remove_breakpoint = xscale_remove_breakpoint,
123 .add_watchpoint = xscale_add_watchpoint,
124 .remove_watchpoint = xscale_remove_watchpoint,
125
126 .register_commands = xscale_register_commands,
127 .target_create = xscale_target_create,
128 .init_target = xscale_init_target,
129 .quit = xscale_quit,
130
131 .virt2phys = xscale_virt2phys,
132 .mmu = xscale_mmu
133 };
134
135 char* xscale_reg_list[] =
136 {
137 "XSCALE_MAINID", /* 0 */
138 "XSCALE_CACHETYPE",
139 "XSCALE_CTRL",
140 "XSCALE_AUXCTRL",
141 "XSCALE_TTB",
142 "XSCALE_DAC",
143 "XSCALE_FSR",
144 "XSCALE_FAR",
145 "XSCALE_PID",
146 "XSCALE_CPACCESS",
147 "XSCALE_IBCR0", /* 10 */
148 "XSCALE_IBCR1",
149 "XSCALE_DBR0",
150 "XSCALE_DBR1",
151 "XSCALE_DBCON",
152 "XSCALE_TBREG",
153 "XSCALE_CHKPT0",
154 "XSCALE_CHKPT1",
155 "XSCALE_DCSR",
156 "XSCALE_TX",
157 "XSCALE_RX", /* 20 */
158 "XSCALE_TXRXCTRL",
159 };
160
161 xscale_reg_t xscale_reg_arch_info[] =
162 {
163 {XSCALE_MAINID, NULL},
164 {XSCALE_CACHETYPE, NULL},
165 {XSCALE_CTRL, NULL},
166 {XSCALE_AUXCTRL, NULL},
167 {XSCALE_TTB, NULL},
168 {XSCALE_DAC, NULL},
169 {XSCALE_FSR, NULL},
170 {XSCALE_FAR, NULL},
171 {XSCALE_PID, NULL},
172 {XSCALE_CPACCESS, NULL},
173 {XSCALE_IBCR0, NULL},
174 {XSCALE_IBCR1, NULL},
175 {XSCALE_DBR0, NULL},
176 {XSCALE_DBR1, NULL},
177 {XSCALE_DBCON, NULL},
178 {XSCALE_TBREG, NULL},
179 {XSCALE_CHKPT0, NULL},
180 {XSCALE_CHKPT1, NULL},
181 {XSCALE_DCSR, NULL}, /* DCSR accessed via JTAG or SW */
182 {-1, NULL}, /* TX accessed via JTAG */
183 {-1, NULL}, /* RX accessed via JTAG */
184 {-1, NULL}, /* TXRXCTRL implicit access via JTAG */
185 };
186
187 int xscale_reg_arch_type = -1;
188
189 int xscale_get_reg(reg_t *reg);
190 int xscale_set_reg(reg_t *reg, u8 *buf);
191
192 int xscale_get_arch_pointers(target_t *target, armv4_5_common_t **armv4_5_p, xscale_common_t **xscale_p)
193 {
194 armv4_5_common_t *armv4_5 = target->arch_info;
195 xscale_common_t *xscale = armv4_5->arch_info;
196
197 if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC)
198 {
199 LOG_ERROR("target isn't an XScale target");
200 return -1;
201 }
202
203 if (xscale->common_magic != XSCALE_COMMON_MAGIC)
204 {
205 LOG_ERROR("target isn't an XScale target");
206 return -1;
207 }
208
209 *armv4_5_p = armv4_5;
210 *xscale_p = xscale;
211
212 return ERROR_OK;
213 }
214
215 int xscale_jtag_set_instr(jtag_tap_t *tap, u32 new_instr)
216 {
217 if (tap==NULL)
218 return ERROR_FAIL;
219
220 if (buf_get_u32(tap->cur_instr, 0, tap->ir_length) != new_instr)
221 {
222 scan_field_t field;
223
224 field.tap = tap;
225 field.num_bits = tap->ir_length;
226 field.out_value = calloc(CEIL(field.num_bits, 8), 1);
227 buf_set_u32(field.out_value, 0, field.num_bits, new_instr);
228 field.out_mask = NULL;
229 field.in_value = NULL;
230 jtag_set_check_value(&field, tap->expected, tap->expected_mask, NULL);
231
232 jtag_add_ir_scan(1, &field, -1);
233
234 free(field.out_value);
235 }
236
237 return ERROR_OK;
238 }
239
240 int xscale_read_dcsr(target_t *target)
241 {
242 armv4_5_common_t *armv4_5 = target->arch_info;
243 xscale_common_t *xscale = armv4_5->arch_info;
244
245 int retval;
246
247 scan_field_t fields[3];
248 u8 field0 = 0x0;
249 u8 field0_check_value = 0x2;
250 u8 field0_check_mask = 0x7;
251 u8 field2 = 0x0;
252 u8 field2_check_value = 0x0;
253 u8 field2_check_mask = 0x1;
254
255 jtag_add_end_state(TAP_PD);
256 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dcsr);
257
258 buf_set_u32(&field0, 1, 1, xscale->hold_rst);
259 buf_set_u32(&field0, 2, 1, xscale->external_debug_break);
260
261 fields[0].tap = xscale->jtag_info.tap;
262 fields[0].num_bits = 3;
263 fields[0].out_value = &field0;
264 fields[0].out_mask = NULL;
265 fields[0].in_value = NULL;
266 jtag_set_check_value(fields+0, &field0_check_value, &field0_check_mask, NULL);
267
268 fields[1].tap = xscale->jtag_info.tap;
269 fields[1].num_bits = 32;
270 fields[1].out_value = NULL;
271 fields[1].out_mask = NULL;
272 fields[1].in_value = xscale->reg_cache->reg_list[XSCALE_DCSR].value;
273 fields[1].in_handler = NULL;
274 fields[1].in_handler_priv = NULL;
275 fields[1].in_check_value = NULL;
276 fields[1].in_check_mask = NULL;
277
278 fields[2].tap = xscale->jtag_info.tap;
279 fields[2].num_bits = 1;
280 fields[2].out_value = &field2;
281 fields[2].out_mask = NULL;
282 fields[2].in_value = NULL;
283 jtag_set_check_value(fields+2, &field2_check_value, &field2_check_mask, NULL);
284
285 jtag_add_dr_scan(3, fields, -1);
286
287 if ((retval = jtag_execute_queue()) != ERROR_OK)
288 {
289 LOG_ERROR("JTAG error while reading DCSR");
290 return retval;
291 }
292
293 xscale->reg_cache->reg_list[XSCALE_DCSR].dirty = 0;
294 xscale->reg_cache->reg_list[XSCALE_DCSR].valid = 1;
295
296 /* write the register with the value we just read
297 * on this second pass, only the first bit of field0 is guaranteed to be 0)
298 */
299 field0_check_mask = 0x1;
300 fields[1].out_value = xscale->reg_cache->reg_list[XSCALE_DCSR].value;
301 fields[1].in_value = NULL;
302
303 jtag_add_end_state(TAP_RTI);
304
305 jtag_add_dr_scan(3, fields, -1);
306
307 /* DANGER!!! this must be here. It will make sure that the arguments
308 * to jtag_set_check_value() does not go out of scope! */
309 return jtag_execute_queue();
310 }
311
312 int xscale_receive(target_t *target, u32 *buffer, int num_words)
313 {
314 if (num_words==0)
315 return ERROR_INVALID_ARGUMENTS;
316
317 int retval=ERROR_OK;
318 armv4_5_common_t *armv4_5 = target->arch_info;
319 xscale_common_t *xscale = armv4_5->arch_info;
320
321 enum tap_state path[3];
322 scan_field_t fields[3];
323
324 u8 *field0 = malloc(num_words * 1);
325 u8 field0_check_value = 0x2;
326 u8 field0_check_mask = 0x6;
327 u32 *field1 = malloc(num_words * 4);
328 u8 field2_check_value = 0x0;
329 u8 field2_check_mask = 0x1;
330 int words_done = 0;
331 int words_scheduled = 0;
332
333 int i;
334
335 path[0] = TAP_SDS;
336 path[1] = TAP_CD;
337 path[2] = TAP_SD;
338
339 fields[0].tap = xscale->jtag_info.tap;
340 fields[0].num_bits = 3;
341 fields[0].out_value = NULL;
342 fields[0].out_mask = NULL;
343 fields[0].in_value = NULL;
344 jtag_set_check_value(fields+0, &field0_check_value, &field0_check_mask, NULL);
345
346 fields[1].tap = xscale->jtag_info.tap;
347 fields[1].num_bits = 32;
348 fields[1].out_value = NULL;
349 fields[1].out_mask = NULL;
350 fields[1].in_value = NULL;
351 fields[1].in_handler = NULL;
352 fields[1].in_handler_priv = NULL;
353 fields[1].in_check_value = NULL;
354 fields[1].in_check_mask = NULL;
355
356
357
358 fields[2].tap = xscale->jtag_info.tap;
359 fields[2].num_bits = 1;
360 fields[2].out_value = NULL;
361 fields[2].out_mask = NULL;
362 fields[2].in_value = NULL;
363 jtag_set_check_value(fields+2, &field2_check_value, &field2_check_mask, NULL);
364
365 jtag_add_end_state(TAP_RTI);
366 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dbgtx);
367 jtag_add_runtest(1, -1); /* ensures that we're in the TAP_RTI state as the above could be a no-op */
368
369 /* repeat until all words have been collected */
370 int attempts=0;
371 while (words_done < num_words)
372 {
373 /* schedule reads */
374 words_scheduled = 0;
375 for (i = words_done; i < num_words; i++)
376 {
377 fields[0].in_value = &field0[i];
378 fields[1].in_handler = buf_to_u32_handler;
379 fields[1].in_handler_priv = (u8*)&field1[i];
380
381 jtag_add_pathmove(3, path);
382 jtag_add_dr_scan(3, fields, TAP_RTI);
383 words_scheduled++;
384 }
385
386 if ((retval = jtag_execute_queue()) != ERROR_OK)
387 {
388 LOG_ERROR("JTAG error while receiving data from debug handler");
389 break;
390 }
391
392 /* examine results */
393 for (i = words_done; i < num_words; i++)
394 {
395 if (!(field0[0] & 1))
396 {
397 /* move backwards if necessary */
398 int j;
399 for (j = i; j < num_words - 1; j++)
400 {
401 field0[j] = field0[j+1];
402 field1[j] = field1[j+1];
403 }
404 words_scheduled--;
405 }
406 }
407 if (words_scheduled==0)
408 {
409 if (attempts++==1000)
410 {
411 LOG_ERROR("Failed to receiving data from debug handler after 1000 attempts");
412 retval=ERROR_TARGET_TIMEOUT;
413 break;
414 }
415 }
416
417 words_done += words_scheduled;
418 }
419
420 for (i = 0; i < num_words; i++)
421 *(buffer++) = buf_get_u32((u8*)&field1[i], 0, 32);
422
423 free(field1);
424
425 return retval;
426 }
427
428 int xscale_read_tx(target_t *target, int consume)
429 {
430 armv4_5_common_t *armv4_5 = target->arch_info;
431 xscale_common_t *xscale = armv4_5->arch_info;
432 enum tap_state path[3];
433 enum tap_state noconsume_path[6];
434
435 int retval;
436 struct timeval timeout, now;
437
438 scan_field_t fields[3];
439 u8 field0_in = 0x0;
440 u8 field0_check_value = 0x2;
441 u8 field0_check_mask = 0x6;
442 u8 field2_check_value = 0x0;
443 u8 field2_check_mask = 0x1;
444
445 jtag_add_end_state(TAP_RTI);
446
447 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dbgtx);
448
449 path[0] = TAP_SDS;
450 path[1] = TAP_CD;
451 path[2] = TAP_SD;
452
453 noconsume_path[0] = TAP_SDS;
454 noconsume_path[1] = TAP_CD;
455 noconsume_path[2] = TAP_E1D;
456 noconsume_path[3] = TAP_PD;
457 noconsume_path[4] = TAP_E2D;
458 noconsume_path[5] = TAP_SD;
459
460 fields[0].tap = xscale->jtag_info.tap;
461 fields[0].num_bits = 3;
462 fields[0].out_value = NULL;
463 fields[0].out_mask = NULL;
464 fields[0].in_value = &field0_in;
465 jtag_set_check_value(fields+0, &field0_check_value, &field0_check_mask, NULL);
466
467 fields[1].tap = xscale->jtag_info.tap;
468 fields[1].num_bits = 32;
469 fields[1].out_value = NULL;
470 fields[1].out_mask = NULL;
471 fields[1].in_value = xscale->reg_cache->reg_list[XSCALE_TX].value;
472 fields[1].in_handler = NULL;
473 fields[1].in_handler_priv = NULL;
474 fields[1].in_check_value = NULL;
475 fields[1].in_check_mask = NULL;
476
477
478
479 fields[2].tap = xscale->jtag_info.tap;
480 fields[2].num_bits = 1;
481 fields[2].out_value = NULL;
482 fields[2].out_mask = NULL;
483 fields[2].in_value = NULL;
484 jtag_set_check_value(fields+2, &field2_check_value, &field2_check_mask, NULL);
485
486 gettimeofday(&timeout, NULL);
487 timeval_add_time(&timeout, 1, 0);
488
489 for (;;)
490 {
491 /* if we want to consume the register content (i.e. clear TX_READY),
492 * we have to go straight from Capture-DR to Shift-DR
493 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
494 */
495 if (consume)
496 jtag_add_pathmove(3, path);
497 else
498 {
499 jtag_add_pathmove(sizeof(noconsume_path)/sizeof(*noconsume_path), noconsume_path);
500 }
501
502 jtag_add_dr_scan(3, fields, TAP_RTI);
503
504 if ((retval = jtag_execute_queue()) != ERROR_OK)
505 {
506 LOG_ERROR("JTAG error while reading TX");
507 return ERROR_TARGET_TIMEOUT;
508 }
509
510 gettimeofday(&now, NULL);
511 if ((now.tv_sec > timeout.tv_sec) || ((now.tv_sec == timeout.tv_sec)&& (now.tv_usec > timeout.tv_usec)))
512 {
513 LOG_ERROR("time out reading TX register");
514 return ERROR_TARGET_TIMEOUT;
515 }
516 if (!((!(field0_in & 1)) && consume))
517 {
518 goto done;
519 }
520 if (debug_level>=3)
521 {
522 LOG_DEBUG("waiting 100ms");
523 alive_sleep(100); /* avoid flooding the logs */
524 } else
525 {
526 keep_alive();
527 }
528 }
529 done:
530
531 if (!(field0_in & 1))
532 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
533
534 return ERROR_OK;
535 }
536
537 int xscale_write_rx(target_t *target)
538 {
539 armv4_5_common_t *armv4_5 = target->arch_info;
540 xscale_common_t *xscale = armv4_5->arch_info;
541
542 int retval;
543 struct timeval timeout, now;
544
545 scan_field_t fields[3];
546 u8 field0_out = 0x0;
547 u8 field0_in = 0x0;
548 u8 field0_check_value = 0x2;
549 u8 field0_check_mask = 0x6;
550 u8 field2 = 0x0;
551 u8 field2_check_value = 0x0;
552 u8 field2_check_mask = 0x1;
553
554 jtag_add_end_state(TAP_RTI);
555
556 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dbgrx);
557
558 fields[0].tap = xscale->jtag_info.tap;
559 fields[0].num_bits = 3;
560 fields[0].out_value = &field0_out;
561 fields[0].out_mask = NULL;
562 fields[0].in_value = &field0_in;
563 jtag_set_check_value(fields+0, &field0_check_value, &field0_check_mask, NULL);
564
565 fields[1].tap = xscale->jtag_info.tap;
566 fields[1].num_bits = 32;
567 fields[1].out_value = xscale->reg_cache->reg_list[XSCALE_RX].value;
568 fields[1].out_mask = NULL;
569 fields[1].in_value = NULL;
570 fields[1].in_handler = NULL;
571 fields[1].in_handler_priv = NULL;
572 fields[1].in_check_value = NULL;
573 fields[1].in_check_mask = NULL;
574
575
576
577 fields[2].tap = xscale->jtag_info.tap;
578 fields[2].num_bits = 1;
579 fields[2].out_value = &field2;
580 fields[2].out_mask = NULL;
581 fields[2].in_value = NULL;
582 jtag_set_check_value(fields+2, &field2_check_value, &field2_check_mask, NULL);
583
584 gettimeofday(&timeout, NULL);
585 timeval_add_time(&timeout, 1, 0);
586
587 /* poll until rx_read is low */
588 LOG_DEBUG("polling RX");
589 for (;;)
590 {
591 jtag_add_dr_scan(3, fields, TAP_RTI);
592
593 if ((retval = jtag_execute_queue()) != ERROR_OK)
594 {
595 LOG_ERROR("JTAG error while writing RX");
596 return retval;
597 }
598
599 gettimeofday(&now, NULL);
600 if ((now.tv_sec > timeout.tv_sec) || ((now.tv_sec == timeout.tv_sec)&& (now.tv_usec > timeout.tv_usec)))
601 {
602 LOG_ERROR("time out writing RX register");
603 return ERROR_TARGET_TIMEOUT;
604 }
605 if (!(field0_in & 1))
606 goto done;
607 if (debug_level>=3)
608 {
609 LOG_DEBUG("waiting 100ms");
610 alive_sleep(100); /* avoid flooding the logs */
611 } else
612 {
613 keep_alive();
614 }
615 }
616 done:
617
618 /* set rx_valid */
619 field2 = 0x1;
620 jtag_add_dr_scan(3, fields, TAP_RTI);
621
622 if ((retval = jtag_execute_queue()) != ERROR_OK)
623 {
624 LOG_ERROR("JTAG error while writing RX");
625 return retval;
626 }
627
628 return ERROR_OK;
629 }
630
631 /* send count elements of size byte to the debug handler */
632 int xscale_send(target_t *target, u8 *buffer, int count, int size)
633 {
634 armv4_5_common_t *armv4_5 = target->arch_info;
635 xscale_common_t *xscale = armv4_5->arch_info;
636 u32 t[3];
637 int bits[3];
638
639 int retval;
640
641 int done_count = 0;
642
643 jtag_add_end_state(TAP_RTI);
644
645 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dbgrx);
646
647 bits[0]=3;
648 t[0]=0;
649 bits[1]=32;
650 t[2]=1;
651 bits[2]=1;
652 int endianness = target->endianness;
653 while (done_count++ < count)
654 {
655 switch (size)
656 {
657 case 4:
658 if (endianness == TARGET_LITTLE_ENDIAN)
659 {
660 t[1]=le_to_h_u32(buffer);
661 } else
662 {
663 t[1]=be_to_h_u32(buffer);
664 }
665 break;
666 case 2:
667 if (endianness == TARGET_LITTLE_ENDIAN)
668 {
669 t[1]=le_to_h_u16(buffer);
670 } else
671 {
672 t[1]=be_to_h_u16(buffer);
673 }
674 break;
675 case 1:
676 t[1]=buffer[0];
677 break;
678 default:
679 LOG_ERROR("BUG: size neither 4, 2 nor 1");
680 exit(-1);
681 }
682 jtag_add_dr_out(xscale->jtag_info.tap,
683 3,
684 bits,
685 t,
686 TAP_RTI);
687 buffer += size;
688 }
689
690 if ((retval = jtag_execute_queue()) != ERROR_OK)
691 {
692 LOG_ERROR("JTAG error while sending data to debug handler");
693 return retval;
694 }
695
696 return ERROR_OK;
697 }
698
699 int xscale_send_u32(target_t *target, u32 value)
700 {
701 armv4_5_common_t *armv4_5 = target->arch_info;
702 xscale_common_t *xscale = armv4_5->arch_info;
703
704 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_RX].value, 0, 32, value);
705 return xscale_write_rx(target);
706 }
707
708 int xscale_write_dcsr(target_t *target, int hold_rst, int ext_dbg_brk)
709 {
710 armv4_5_common_t *armv4_5 = target->arch_info;
711 xscale_common_t *xscale = armv4_5->arch_info;
712
713 int retval;
714
715 scan_field_t fields[3];
716 u8 field0 = 0x0;
717 u8 field0_check_value = 0x2;
718 u8 field0_check_mask = 0x7;
719 u8 field2 = 0x0;
720 u8 field2_check_value = 0x0;
721 u8 field2_check_mask = 0x1;
722
723 if (hold_rst != -1)
724 xscale->hold_rst = hold_rst;
725
726 if (ext_dbg_brk != -1)
727 xscale->external_debug_break = ext_dbg_brk;
728
729 jtag_add_end_state(TAP_RTI);
730 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dcsr);
731
732 buf_set_u32(&field0, 1, 1, xscale->hold_rst);
733 buf_set_u32(&field0, 2, 1, xscale->external_debug_break);
734
735 fields[0].tap = xscale->jtag_info.tap;
736 fields[0].num_bits = 3;
737 fields[0].out_value = &field0;
738 fields[0].out_mask = NULL;
739 fields[0].in_value = NULL;
740 jtag_set_check_value(fields+0, &field0_check_value, &field0_check_mask, NULL);
741
742 fields[1].tap = xscale->jtag_info.tap;
743 fields[1].num_bits = 32;
744 fields[1].out_value = xscale->reg_cache->reg_list[XSCALE_DCSR].value;
745 fields[1].out_mask = NULL;
746 fields[1].in_value = NULL;
747 fields[1].in_handler = NULL;
748 fields[1].in_handler_priv = NULL;
749 fields[1].in_check_value = NULL;
750 fields[1].in_check_mask = NULL;
751
752
753
754 fields[2].tap = xscale->jtag_info.tap;
755 fields[2].num_bits = 1;
756 fields[2].out_value = &field2;
757 fields[2].out_mask = NULL;
758 fields[2].in_value = NULL;
759 jtag_set_check_value(fields+2, &field2_check_value, &field2_check_mask, NULL);
760
761 jtag_add_dr_scan(3, fields, -1);
762
763 if ((retval = jtag_execute_queue()) != ERROR_OK)
764 {
765 LOG_ERROR("JTAG error while writing DCSR");
766 return retval;
767 }
768
769 xscale->reg_cache->reg_list[XSCALE_DCSR].dirty = 0;
770 xscale->reg_cache->reg_list[XSCALE_DCSR].valid = 1;
771
772 return ERROR_OK;
773 }
774
775 /* parity of the number of bits 0 if even; 1 if odd. for 32 bit words */
776 unsigned int parity (unsigned int v)
777 {
778 unsigned int ov = v;
779 v ^= v >> 16;
780 v ^= v >> 8;
781 v ^= v >> 4;
782 v &= 0xf;
783 LOG_DEBUG("parity of 0x%x is %i", ov, (0x6996 >> v) & 1);
784 return (0x6996 >> v) & 1;
785 }
786
787 int xscale_load_ic(target_t *target, int mini, u32 va, u32 buffer[8])
788 {
789 armv4_5_common_t *armv4_5 = target->arch_info;
790 xscale_common_t *xscale = armv4_5->arch_info;
791 u8 packet[4];
792 u8 cmd;
793 int word;
794
795 scan_field_t fields[2];
796
797 LOG_DEBUG("loading miniIC at 0x%8.8x", va);
798
799 jtag_add_end_state(TAP_RTI);
800 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.ldic); /* LDIC */
801
802 /* CMD is b010 for Main IC and b011 for Mini IC */
803 if (mini)
804 buf_set_u32(&cmd, 0, 3, 0x3);
805 else
806 buf_set_u32(&cmd, 0, 3, 0x2);
807
808 buf_set_u32(&cmd, 3, 3, 0x0);
809
810 /* virtual address of desired cache line */
811 buf_set_u32(packet, 0, 27, va >> 5);
812
813 fields[0].tap = xscale->jtag_info.tap;
814 fields[0].num_bits = 6;
815 fields[0].out_value = &cmd;
816 fields[0].out_mask = NULL;
817 fields[0].in_value = NULL;
818 fields[0].in_check_value = NULL;
819 fields[0].in_check_mask = NULL;
820 fields[0].in_handler = NULL;
821 fields[0].in_handler_priv = NULL;
822
823 fields[1].tap = xscale->jtag_info.tap;
824 fields[1].num_bits = 27;
825 fields[1].out_value = packet;
826 fields[1].out_mask = NULL;
827 fields[1].in_value = NULL;
828 fields[1].in_check_value = NULL;
829 fields[1].in_check_mask = NULL;
830 fields[1].in_handler = NULL;
831 fields[1].in_handler_priv = NULL;
832
833 jtag_add_dr_scan(2, fields, -1);
834
835 fields[0].num_bits = 32;
836 fields[0].out_value = packet;
837
838 fields[1].num_bits = 1;
839 fields[1].out_value = &cmd;
840
841 for (word = 0; word < 8; word++)
842 {
843 buf_set_u32(packet, 0, 32, buffer[word]);
844 cmd = parity(*((u32*)packet));
845 jtag_add_dr_scan(2, fields, -1);
846 }
847
848 jtag_execute_queue();
849
850 return ERROR_OK;
851 }
852
853 int xscale_invalidate_ic_line(target_t *target, u32 va)
854 {
855 armv4_5_common_t *armv4_5 = target->arch_info;
856 xscale_common_t *xscale = armv4_5->arch_info;
857 u8 packet[4];
858 u8 cmd;
859
860 scan_field_t fields[2];
861
862 jtag_add_end_state(TAP_RTI);
863 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.ldic); /* LDIC */
864
865 /* CMD for invalidate IC line b000, bits [6:4] b000 */
866 buf_set_u32(&cmd, 0, 6, 0x0);
867
868 /* virtual address of desired cache line */
869 buf_set_u32(packet, 0, 27, va >> 5);
870
871 fields[0].tap = xscale->jtag_info.tap;
872 fields[0].num_bits = 6;
873 fields[0].out_value = &cmd;
874 fields[0].out_mask = NULL;
875 fields[0].in_value = NULL;
876 fields[0].in_check_value = NULL;
877 fields[0].in_check_mask = NULL;
878 fields[0].in_handler = NULL;
879 fields[0].in_handler_priv = NULL;
880
881 fields[1].tap = xscale->jtag_info.tap;
882 fields[1].num_bits = 27;
883 fields[1].out_value = packet;
884 fields[1].out_mask = NULL;
885 fields[1].in_value = NULL;
886 fields[1].in_check_value = NULL;
887 fields[1].in_check_mask = NULL;
888 fields[1].in_handler = NULL;
889 fields[1].in_handler_priv = NULL;
890
891 jtag_add_dr_scan(2, fields, -1);
892
893 return ERROR_OK;
894 }
895
896 int xscale_update_vectors(target_t *target)
897 {
898 armv4_5_common_t *armv4_5 = target->arch_info;
899 xscale_common_t *xscale = armv4_5->arch_info;
900 int i;
901 int retval;
902
903 u32 low_reset_branch, high_reset_branch;
904
905 for (i = 1; i < 8; i++)
906 {
907 /* if there's a static vector specified for this exception, override */
908 if (xscale->static_high_vectors_set & (1 << i))
909 {
910 xscale->high_vectors[i] = xscale->static_high_vectors[i];
911 }
912 else
913 {
914 retval=target_read_u32(target, 0xffff0000 + 4*i, &xscale->high_vectors[i]);
915 if (retval == ERROR_TARGET_TIMEOUT)
916 return retval;
917 if (retval!=ERROR_OK)
918 {
919 /* Some of these reads will fail as part of normal execution */
920 xscale->high_vectors[i] = ARMV4_5_B(0xfffffe, 0);
921 }
922 }
923 }
924
925 for (i = 1; i < 8; i++)
926 {
927 if (xscale->static_low_vectors_set & (1 << i))
928 {
929 xscale->low_vectors[i] = xscale->static_low_vectors[i];
930 }
931 else
932 {
933 retval=target_read_u32(target, 0x0 + 4*i, &xscale->low_vectors[i]);
934 if (retval == ERROR_TARGET_TIMEOUT)
935 return retval;
936 if (retval!=ERROR_OK)
937 {
938 /* Some of these reads will fail as part of normal execution */
939 xscale->low_vectors[i] = ARMV4_5_B(0xfffffe, 0);
940 }
941 }
942 }
943
944 /* calculate branches to debug handler */
945 low_reset_branch = (xscale->handler_address + 0x20 - 0x0 - 0x8) >> 2;
946 high_reset_branch = (xscale->handler_address + 0x20 - 0xffff0000 - 0x8) >> 2;
947
948 xscale->low_vectors[0] = ARMV4_5_B((low_reset_branch & 0xffffff), 0);
949 xscale->high_vectors[0] = ARMV4_5_B((high_reset_branch & 0xffffff), 0);
950
951 /* invalidate and load exception vectors in mini i-cache */
952 xscale_invalidate_ic_line(target, 0x0);
953 xscale_invalidate_ic_line(target, 0xffff0000);
954
955 xscale_load_ic(target, 1, 0x0, xscale->low_vectors);
956 xscale_load_ic(target, 1, 0xffff0000, xscale->high_vectors);
957
958 return ERROR_OK;
959 }
960
961 int xscale_arch_state(struct target_s *target)
962 {
963 armv4_5_common_t *armv4_5 = target->arch_info;
964 xscale_common_t *xscale = armv4_5->arch_info;
965
966 char *state[] =
967 {
968 "disabled", "enabled"
969 };
970
971 char *arch_dbg_reason[] =
972 {
973 "", "\n(processor reset)", "\n(trace buffer full)"
974 };
975
976 if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC)
977 {
978 LOG_ERROR("BUG: called for a non-ARMv4/5 target");
979 exit(-1);
980 }
981
982 LOG_USER("target halted in %s state due to %s, current mode: %s\n"
983 "cpsr: 0x%8.8x pc: 0x%8.8x\n"
984 "MMU: %s, D-Cache: %s, I-Cache: %s"
985 "%s",
986 armv4_5_state_strings[armv4_5->core_state],
987 Jim_Nvp_value2name_simple( nvp_target_debug_reason, target->debug_reason )->name ,
988 armv4_5_mode_strings[armv4_5_mode_to_number(armv4_5->core_mode)],
989 buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32),
990 buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32),
991 state[xscale->armv4_5_mmu.mmu_enabled],
992 state[xscale->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled],
993 state[xscale->armv4_5_mmu.armv4_5_cache.i_cache_enabled],
994 arch_dbg_reason[xscale->arch_debug_reason]);
995
996 return ERROR_OK;
997 }
998
999 int xscale_poll(target_t *target)
1000 {
1001 int retval=ERROR_OK;
1002 armv4_5_common_t *armv4_5 = target->arch_info;
1003 xscale_common_t *xscale = armv4_5->arch_info;
1004
1005 if ((target->state == TARGET_RUNNING) || (target->state == TARGET_DEBUG_RUNNING))
1006 {
1007 enum target_state previous_state = target->state;
1008 if ((retval = xscale_read_tx(target, 0)) == ERROR_OK)
1009 {
1010
1011 /* there's data to read from the tx register, we entered debug state */
1012 xscale->handler_running = 1;
1013
1014 target->state = TARGET_HALTED;
1015
1016 /* process debug entry, fetching current mode regs */
1017 retval = xscale_debug_entry(target);
1018 }
1019 else if (retval != ERROR_TARGET_RESOURCE_NOT_AVAILABLE)
1020 {
1021 LOG_USER("error while polling TX register, reset CPU");
1022 /* here we "lie" so GDB won't get stuck and a reset can be perfomed */
1023 target->state = TARGET_HALTED;
1024 }
1025
1026 /* debug_entry could have overwritten target state (i.e. immediate resume)
1027 * don't signal event handlers in that case
1028 */
1029 if (target->state != TARGET_HALTED)
1030 return ERROR_OK;
1031
1032 /* if target was running, signal that we halted
1033 * otherwise we reentered from debug execution */
1034 if (previous_state == TARGET_RUNNING)
1035 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
1036 else
1037 target_call_event_callbacks(target, TARGET_EVENT_DEBUG_HALTED);
1038 }
1039
1040 return retval;
1041 }
1042
1043 int xscale_debug_entry(target_t *target)
1044 {
1045 armv4_5_common_t *armv4_5 = target->arch_info;
1046 xscale_common_t *xscale = armv4_5->arch_info;
1047 u32 pc;
1048 u32 buffer[10];
1049 int i;
1050 int retval;
1051
1052 u32 moe;
1053
1054 /* clear external dbg break (will be written on next DCSR read) */
1055 xscale->external_debug_break = 0;
1056 if ((retval=xscale_read_dcsr(target))!=ERROR_OK)
1057 return retval;
1058
1059 /* get r0, pc, r1 to r7 and cpsr */
1060 if ((retval=xscale_receive(target, buffer, 10))!=ERROR_OK)
1061 return retval;
1062
1063 /* move r0 from buffer to register cache */
1064 buf_set_u32(armv4_5->core_cache->reg_list[0].value, 0, 32, buffer[0]);
1065 armv4_5->core_cache->reg_list[15].dirty = 1;
1066 armv4_5->core_cache->reg_list[15].valid = 1;
1067 LOG_DEBUG("r0: 0x%8.8x", buffer[0]);
1068
1069 /* move pc from buffer to register cache */
1070 buf_set_u32(armv4_5->core_cache->reg_list[15].value, 0, 32, buffer[1]);
1071 armv4_5->core_cache->reg_list[15].dirty = 1;
1072 armv4_5->core_cache->reg_list[15].valid = 1;
1073 LOG_DEBUG("pc: 0x%8.8x", buffer[1]);
1074
1075 /* move data from buffer to register cache */
1076 for (i = 1; i <= 7; i++)
1077 {
1078 buf_set_u32(armv4_5->core_cache->reg_list[i].value, 0, 32, buffer[1 + i]);
1079 armv4_5->core_cache->reg_list[i].dirty = 1;
1080 armv4_5->core_cache->reg_list[i].valid = 1;
1081 LOG_DEBUG("r%i: 0x%8.8x", i, buffer[i + 1]);
1082 }
1083
1084 buf_set_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32, buffer[9]);
1085 armv4_5->core_cache->reg_list[ARMV4_5_CPSR].dirty = 1;
1086 armv4_5->core_cache->reg_list[ARMV4_5_CPSR].valid = 1;
1087 LOG_DEBUG("cpsr: 0x%8.8x", buffer[9]);
1088
1089 armv4_5->core_mode = buffer[9] & 0x1f;
1090 if (armv4_5_mode_to_number(armv4_5->core_mode) == -1)
1091 {
1092 target->state = TARGET_UNKNOWN;
1093 LOG_ERROR("cpsr contains invalid mode value - communication failure");
1094 return ERROR_TARGET_FAILURE;
1095 }
1096 LOG_DEBUG("target entered debug state in %s mode", armv4_5_mode_strings[armv4_5_mode_to_number(armv4_5->core_mode)]);
1097
1098 if (buffer[9] & 0x20)
1099 armv4_5->core_state = ARMV4_5_STATE_THUMB;
1100 else
1101 armv4_5->core_state = ARMV4_5_STATE_ARM;
1102
1103
1104 if (armv4_5_mode_to_number(armv4_5->core_mode)==-1)
1105 return ERROR_FAIL;
1106
1107 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1108 if ((armv4_5->core_mode != ARMV4_5_MODE_USR) && (armv4_5->core_mode != ARMV4_5_MODE_SYS))
1109 {
1110 xscale_receive(target, buffer, 8);
1111 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).value, 0, 32, buffer[7]);
1112 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).dirty = 0;
1113 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).valid = 1;
1114 }
1115 else
1116 {
1117 /* r8 to r14, but no spsr */
1118 xscale_receive(target, buffer, 7);
1119 }
1120
1121 /* move data from buffer to register cache */
1122 for (i = 8; i <= 14; i++)
1123 {
1124 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).value, 0, 32, buffer[i - 8]);
1125 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).dirty = 0;
1126 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).valid = 1;
1127 }
1128
1129 /* examine debug reason */
1130 xscale_read_dcsr(target);
1131 moe = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 2, 3);
1132
1133 /* stored PC (for calculating fixup) */
1134 pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
1135
1136 switch (moe)
1137 {
1138 case 0x0: /* Processor reset */
1139 target->debug_reason = DBG_REASON_DBGRQ;
1140 xscale->arch_debug_reason = XSCALE_DBG_REASON_RESET;
1141 pc -= 4;
1142 break;
1143 case 0x1: /* Instruction breakpoint hit */
1144 target->debug_reason = DBG_REASON_BREAKPOINT;
1145 xscale->arch_debug_reason = XSCALE_DBG_REASON_GENERIC;
1146 pc -= 4;
1147 break;
1148 case 0x2: /* Data breakpoint hit */
1149 target->debug_reason = DBG_REASON_WATCHPOINT;
1150 xscale->arch_debug_reason = XSCALE_DBG_REASON_GENERIC;
1151 pc -= 4;
1152 break;
1153 case 0x3: /* BKPT instruction executed */
1154 target->debug_reason = DBG_REASON_BREAKPOINT;
1155 xscale->arch_debug_reason = XSCALE_DBG_REASON_GENERIC;
1156 pc -= 4;
1157 break;
1158 case 0x4: /* Ext. debug event */
1159 target->debug_reason = DBG_REASON_DBGRQ;
1160 xscale->arch_debug_reason = XSCALE_DBG_REASON_GENERIC;
1161 pc -= 4;
1162 break;
1163 case 0x5: /* Vector trap occured */
1164 target->debug_reason = DBG_REASON_BREAKPOINT;
1165 xscale->arch_debug_reason = XSCALE_DBG_REASON_GENERIC;
1166 pc -= 4;
1167 break;
1168 case 0x6: /* Trace buffer full break */
1169 target->debug_reason = DBG_REASON_DBGRQ;
1170 xscale->arch_debug_reason = XSCALE_DBG_REASON_TB_FULL;
1171 pc -= 4;
1172 break;
1173 case 0x7: /* Reserved */
1174 default:
1175 LOG_ERROR("Method of Entry is 'Reserved'");
1176 exit(-1);
1177 break;
1178 }
1179
1180 /* apply PC fixup */
1181 buf_set_u32(armv4_5->core_cache->reg_list[15].value, 0, 32, pc);
1182
1183 /* on the first debug entry, identify cache type */
1184 if (xscale->armv4_5_mmu.armv4_5_cache.ctype == -1)
1185 {
1186 u32 cache_type_reg;
1187
1188 /* read cp15 cache type register */
1189 xscale_get_reg(&xscale->reg_cache->reg_list[XSCALE_CACHETYPE]);
1190 cache_type_reg = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_CACHETYPE].value, 0, 32);
1191
1192 armv4_5_identify_cache(cache_type_reg, &xscale->armv4_5_mmu.armv4_5_cache);
1193 }
1194
1195 /* examine MMU and Cache settings */
1196 /* read cp15 control register */
1197 xscale_get_reg(&xscale->reg_cache->reg_list[XSCALE_CTRL]);
1198 xscale->cp15_control_reg = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_CTRL].value, 0, 32);
1199 xscale->armv4_5_mmu.mmu_enabled = (xscale->cp15_control_reg & 0x1U) ? 1 : 0;
1200 xscale->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled = (xscale->cp15_control_reg & 0x4U) ? 1 : 0;
1201 xscale->armv4_5_mmu.armv4_5_cache.i_cache_enabled = (xscale->cp15_control_reg & 0x1000U) ? 1 : 0;
1202
1203 /* tracing enabled, read collected trace data */
1204 if (xscale->trace.buffer_enabled)
1205 {
1206 xscale_read_trace(target);
1207 xscale->trace.buffer_fill--;
1208
1209 /* resume if we're still collecting trace data */
1210 if ((xscale->arch_debug_reason == XSCALE_DBG_REASON_TB_FULL)
1211 && (xscale->trace.buffer_fill > 0))
1212 {
1213 xscale_resume(target, 1, 0x0, 1, 0);
1214 }
1215 else
1216 {
1217 xscale->trace.buffer_enabled = 0;
1218 }
1219 }
1220
1221 return ERROR_OK;
1222 }
1223
1224 int xscale_halt(target_t *target)
1225 {
1226 armv4_5_common_t *armv4_5 = target->arch_info;
1227 xscale_common_t *xscale = armv4_5->arch_info;
1228
1229 LOG_DEBUG("target->state: %s",
1230 Jim_Nvp_value2name_simple( nvp_target_state, target->state )->name);
1231
1232 if (target->state == TARGET_HALTED)
1233 {
1234 LOG_DEBUG("target was already halted");
1235 return ERROR_OK;
1236 }
1237 else if (target->state == TARGET_UNKNOWN)
1238 {
1239 /* this must not happen for a xscale target */
1240 LOG_ERROR("target was in unknown state when halt was requested");
1241 return ERROR_TARGET_INVALID;
1242 }
1243 else if (target->state == TARGET_RESET)
1244 {
1245 LOG_DEBUG("target->state == TARGET_RESET");
1246 }
1247 else
1248 {
1249 /* assert external dbg break */
1250 xscale->external_debug_break = 1;
1251 xscale_read_dcsr(target);
1252
1253 target->debug_reason = DBG_REASON_DBGRQ;
1254 }
1255
1256 return ERROR_OK;
1257 }
1258
1259 int xscale_enable_single_step(struct target_s *target, u32 next_pc)
1260 {
1261 armv4_5_common_t *armv4_5 = target->arch_info;
1262 xscale_common_t *xscale= armv4_5->arch_info;
1263 reg_t *ibcr0 = &xscale->reg_cache->reg_list[XSCALE_IBCR0];
1264 int retval;
1265
1266 if (xscale->ibcr0_used)
1267 {
1268 breakpoint_t *ibcr0_bp = breakpoint_find(target, buf_get_u32(ibcr0->value, 0, 32) & 0xfffffffe);
1269
1270 if (ibcr0_bp)
1271 {
1272 xscale_unset_breakpoint(target, ibcr0_bp);
1273 }
1274 else
1275 {
1276 LOG_ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1277 exit(-1);
1278 }
1279 }
1280
1281 if ((retval=xscale_set_reg_u32(ibcr0, next_pc | 0x1))!=ERROR_OK)
1282 return retval;
1283
1284 return ERROR_OK;
1285 }
1286
1287 int xscale_disable_single_step(struct target_s *target)
1288 {
1289 armv4_5_common_t *armv4_5 = target->arch_info;
1290 xscale_common_t *xscale= armv4_5->arch_info;
1291 reg_t *ibcr0 = &xscale->reg_cache->reg_list[XSCALE_IBCR0];
1292 int retval;
1293
1294 if ((retval=xscale_set_reg_u32(ibcr0, 0x0))!=ERROR_OK)
1295 return retval;
1296
1297 return ERROR_OK;
1298 }
1299
1300 int xscale_resume(struct target_s *target, int current, u32 address, int handle_breakpoints, int debug_execution)
1301 {
1302 armv4_5_common_t *armv4_5 = target->arch_info;
1303 xscale_common_t *xscale= armv4_5->arch_info;
1304 breakpoint_t *breakpoint = target->breakpoints;
1305
1306 u32 current_pc;
1307
1308 int retval;
1309 int i;
1310
1311 LOG_DEBUG("-");
1312
1313 if (target->state != TARGET_HALTED)
1314 {
1315 LOG_WARNING("target not halted");
1316 return ERROR_TARGET_NOT_HALTED;
1317 }
1318
1319 if (!debug_execution)
1320 {
1321 target_free_all_working_areas(target);
1322 }
1323
1324 /* update vector tables */
1325 if ((retval=xscale_update_vectors(target))!=ERROR_OK)
1326 return retval;
1327
1328 /* current = 1: continue on current pc, otherwise continue at <address> */
1329 if (!current)
1330 buf_set_u32(armv4_5->core_cache->reg_list[15].value, 0, 32, address);
1331
1332 current_pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
1333
1334 /* if we're at the reset vector, we have to simulate the branch */
1335 if (current_pc == 0x0)
1336 {
1337 arm_simulate_step(target, NULL);
1338 current_pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
1339 }
1340
1341 /* the front-end may request us not to handle breakpoints */
1342 if (handle_breakpoints)
1343 {
1344 if ((breakpoint = breakpoint_find(target, buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32))))
1345 {
1346 u32 next_pc;
1347
1348 /* there's a breakpoint at the current PC, we have to step over it */
1349 LOG_DEBUG("unset breakpoint at 0x%8.8x", breakpoint->address);
1350 xscale_unset_breakpoint(target, breakpoint);
1351
1352 /* calculate PC of next instruction */
1353 if ((retval = arm_simulate_step(target, &next_pc)) != ERROR_OK)
1354 {
1355 u32 current_opcode;
1356 target_read_u32(target, current_pc, &current_opcode);
1357 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode);
1358 }
1359
1360 LOG_DEBUG("enable single-step");
1361 xscale_enable_single_step(target, next_pc);
1362
1363 /* restore banked registers */
1364 xscale_restore_context(target);
1365
1366 /* send resume request (command 0x30 or 0x31)
1367 * clean the trace buffer if it is to be enabled (0x62) */
1368 if (xscale->trace.buffer_enabled)
1369 {
1370 xscale_send_u32(target, 0x62);
1371 xscale_send_u32(target, 0x31);
1372 }
1373 else
1374 xscale_send_u32(target, 0x30);
1375
1376 /* send CPSR */
1377 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32));
1378 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32));
1379
1380 for (i = 7; i >= 0; i--)
1381 {
1382 /* send register */
1383 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32));
1384 LOG_DEBUG("writing r%i with value 0x%8.8x", i, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32));
1385 }
1386
1387 /* send PC */
1388 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32));
1389 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32));
1390
1391 /* wait for and process debug entry */
1392 xscale_debug_entry(target);
1393
1394 LOG_DEBUG("disable single-step");
1395 xscale_disable_single_step(target);
1396
1397 LOG_DEBUG("set breakpoint at 0x%8.8x", breakpoint->address);
1398 xscale_set_breakpoint(target, breakpoint);
1399 }
1400 }
1401
1402 /* enable any pending breakpoints and watchpoints */
1403 xscale_enable_breakpoints(target);
1404 xscale_enable_watchpoints(target);
1405
1406 /* restore banked registers */
1407 xscale_restore_context(target);
1408
1409 /* send resume request (command 0x30 or 0x31)
1410 * clean the trace buffer if it is to be enabled (0x62) */
1411 if (xscale->trace.buffer_enabled)
1412 {
1413 xscale_send_u32(target, 0x62);
1414 xscale_send_u32(target, 0x31);
1415 }
1416 else
1417 xscale_send_u32(target, 0x30);
1418
1419 /* send CPSR */
1420 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32));
1421 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32));
1422
1423 for (i = 7; i >= 0; i--)
1424 {
1425 /* send register */
1426 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32));
1427 LOG_DEBUG("writing r%i with value 0x%8.8x", i, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32));
1428 }
1429
1430 /* send PC */
1431 xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32));
1432 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32));
1433
1434 target->debug_reason = DBG_REASON_NOTHALTED;
1435
1436 if (!debug_execution)
1437 {
1438 /* registers are now invalid */
1439 armv4_5_invalidate_core_regs(target);
1440 target->state = TARGET_RUNNING;
1441 target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
1442 }
1443 else
1444 {
1445 target->state = TARGET_DEBUG_RUNNING;
1446 target_call_event_callbacks(target, TARGET_EVENT_DEBUG_RESUMED);
1447 }
1448
1449 LOG_DEBUG("target resumed");
1450
1451 xscale->handler_running = 1;
1452
1453 return ERROR_OK;
1454 }
1455
1456 static int xscale_step_inner(struct target_s *target, int current, u32 address, int handle_breakpoints)
1457 {
1458 armv4_5_common_t *armv4_5 = target->arch_info;
1459 xscale_common_t *xscale = armv4_5->arch_info;
1460
1461 u32 current_pc, next_pc;
1462 int retval;
1463 int i;
1464
1465
1466 target->debug_reason = DBG_REASON_SINGLESTEP;
1467
1468 /* calculate PC of next instruction */
1469 if ((retval = arm_simulate_step(target, &next_pc)) != ERROR_OK)
1470 {
1471 u32 current_opcode;
1472 target_read_u32(target, current_pc, &current_opcode);
1473 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode);
1474 return retval;
1475 }
1476
1477 LOG_DEBUG("enable single-step");
1478 if ((retval=xscale_enable_single_step(target, next_pc))!=ERROR_OK)
1479 return retval;
1480
1481 /* restore banked registers */
1482 if ((retval=xscale_restore_context(target))!=ERROR_OK)
1483 return retval;
1484
1485 /* send resume request (command 0x30 or 0x31)
1486 * clean the trace buffer if it is to be enabled (0x62) */
1487 if (xscale->trace.buffer_enabled)
1488 {
1489 if ((retval=xscale_send_u32(target, 0x62))!=ERROR_OK)
1490 return retval;
1491 if ((retval=xscale_send_u32(target, 0x31))!=ERROR_OK)
1492 return retval;
1493 }
1494 else
1495 if ((retval=xscale_send_u32(target, 0x30))!=ERROR_OK)
1496 return retval;
1497
1498 /* send CPSR */
1499 if ((retval=xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32)))!=ERROR_OK)
1500 return retval;
1501 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32));
1502
1503 for (i = 7; i >= 0; i--)
1504 {
1505 /* send register */
1506 if ((retval=xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32)))!=ERROR_OK)
1507 return retval;
1508 LOG_DEBUG("writing r%i with value 0x%8.8x", i, buf_get_u32(armv4_5->core_cache->reg_list[i].value, 0, 32));
1509 }
1510
1511 /* send PC */
1512 if ((retval=xscale_send_u32(target, buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32)))!=ERROR_OK)
1513 return retval;
1514 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32));
1515
1516 target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
1517
1518 /* registers are now invalid */
1519 if ((retval=armv4_5_invalidate_core_regs(target))!=ERROR_OK)
1520 return retval;
1521
1522 /* wait for and process debug entry */
1523 if ((retval=xscale_debug_entry(target))!=ERROR_OK)
1524 return retval;
1525
1526 LOG_DEBUG("disable single-step");
1527 if ((retval=xscale_disable_single_step(target))!=ERROR_OK)
1528 return retval;
1529
1530 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
1531
1532 return ERROR_OK;
1533 }
1534
1535 int xscale_step(struct target_s *target, int current, u32 address, int handle_breakpoints)
1536 {
1537 armv4_5_common_t *armv4_5 = target->arch_info;
1538 breakpoint_t *breakpoint = target->breakpoints;
1539
1540 u32 current_pc;
1541 int retval;
1542
1543 if (target->state != TARGET_HALTED)
1544 {
1545 LOG_WARNING("target not halted");
1546 return ERROR_TARGET_NOT_HALTED;
1547 }
1548
1549 /* current = 1: continue on current pc, otherwise continue at <address> */
1550 if (!current)
1551 buf_set_u32(armv4_5->core_cache->reg_list[15].value, 0, 32, address);
1552
1553 current_pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
1554
1555 /* if we're at the reset vector, we have to simulate the step */
1556 if (current_pc == 0x0)
1557 {
1558 if ((retval=arm_simulate_step(target, NULL))!=ERROR_OK)
1559 return retval;
1560 current_pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
1561
1562 target->debug_reason = DBG_REASON_SINGLESTEP;
1563 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
1564
1565 return ERROR_OK;
1566 }
1567
1568 /* the front-end may request us not to handle breakpoints */
1569 if (handle_breakpoints)
1570 if ((breakpoint = breakpoint_find(target, buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32))))
1571 {
1572 if ((retval=xscale_unset_breakpoint(target, breakpoint))!=ERROR_OK)
1573 return retval;
1574 }
1575
1576 retval = xscale_step_inner(target, current, address, handle_breakpoints);
1577
1578 if (breakpoint)
1579 {
1580 xscale_set_breakpoint(target, breakpoint);
1581 }
1582
1583 LOG_DEBUG("target stepped");
1584
1585 return ERROR_OK;
1586
1587 }
1588
1589 int xscale_assert_reset(target_t *target)
1590 {
1591 armv4_5_common_t *armv4_5 = target->arch_info;
1592 xscale_common_t *xscale = armv4_5->arch_info;
1593
1594 LOG_DEBUG("target->state: %s",
1595 Jim_Nvp_value2name_simple( nvp_target_state, target->state )->name);
1596
1597 /* select DCSR instruction (set endstate to R-T-I to ensure we don't
1598 * end up in T-L-R, which would reset JTAG
1599 */
1600 jtag_add_end_state(TAP_RTI);
1601 xscale_jtag_set_instr(xscale->jtag_info.tap, xscale->jtag_info.dcsr);
1602
1603 /* set Hold reset, Halt mode and Trap Reset */
1604 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 30, 1, 0x1);
1605 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 16, 1, 0x1);
1606 xscale_write_dcsr(target, 1, 0);
1607
1608 /* select BYPASS, because having DCSR selected caused problems on the PXA27x */
1609 xscale_jtag_set_instr(xscale->jtag_info.tap, 0x7f);
1610 jtag_execute_queue();
1611
1612 /* assert reset */
1613 jtag_add_reset(0, 1);
1614
1615 /* sleep 1ms, to be sure we fulfill any requirements */
1616 jtag_add_sleep(1000);
1617 jtag_execute_queue();
1618
1619 target->state = TARGET_RESET;
1620
1621 if (target->reset_halt)
1622 {
1623 int retval;
1624 if ((retval = target_halt(target))!=ERROR_OK)
1625 return retval;
1626 }
1627
1628 return ERROR_OK;
1629 }
1630
1631 int xscale_deassert_reset(target_t *target)
1632 {
1633 armv4_5_common_t *armv4_5 = target->arch_info;
1634 xscale_common_t *xscale = armv4_5->arch_info;
1635
1636 fileio_t debug_handler;
1637 u32 address;
1638 u32 binary_size;
1639
1640 u32 buf_cnt;
1641 int i;
1642 int retval;
1643
1644 breakpoint_t *breakpoint = target->breakpoints;
1645
1646 LOG_DEBUG("-");
1647
1648 xscale->ibcr_available = 2;
1649 xscale->ibcr0_used = 0;
1650 xscale->ibcr1_used = 0;
1651
1652 xscale->dbr_available = 2;
1653 xscale->dbr0_used = 0;
1654 xscale->dbr1_used = 0;
1655
1656 /* mark all hardware breakpoints as unset */
1657 while (breakpoint)
1658 {
1659 if (breakpoint->type == BKPT_HARD)
1660 {
1661 breakpoint->set = 0;
1662 }
1663 breakpoint = breakpoint->next;
1664 }
1665
1666 if (!xscale->handler_installed)
1667 {
1668 /* release SRST */
1669 jtag_add_reset(0, 0);
1670
1671 /* wait 300ms; 150 and 100ms were not enough */
1672 jtag_add_sleep(300*1000);
1673
1674 jtag_add_runtest(2030, TAP_RTI);
1675 jtag_execute_queue();
1676
1677 /* set Hold reset, Halt mode and Trap Reset */
1678 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 30, 1, 0x1);
1679 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 16, 1, 0x1);
1680 xscale_write_dcsr(target, 1, 0);
1681
1682 /* Load debug handler */
1683 if (fileio_open(&debug_handler, "xscale/debug_handler.bin", FILEIO_READ, FILEIO_BINARY) != ERROR_OK)
1684 {
1685 return ERROR_OK;
1686 }
1687
1688 if ((binary_size = debug_handler.size) % 4)
1689 {
1690 LOG_ERROR("debug_handler.bin: size not a multiple of 4");
1691 exit(-1);
1692 }
1693
1694 if (binary_size > 0x800)
1695 {
1696 LOG_ERROR("debug_handler.bin: larger than 2kb");
1697 exit(-1);
1698 }
1699
1700 binary_size = CEIL(binary_size, 32) * 32;
1701
1702 address = xscale->handler_address;
1703 while (binary_size > 0)
1704 {
1705 u32 cache_line[8];
1706 u8 buffer[32];
1707
1708 if ((retval = fileio_read(&debug_handler, 32, buffer, &buf_cnt)) != ERROR_OK)
1709 {
1710
1711 }
1712
1713 for (i = 0; i < buf_cnt; i += 4)
1714 {
1715 /* convert LE buffer to host-endian u32 */
1716 cache_line[i / 4] = le_to_h_u32(&buffer[i]);
1717 }
1718
1719 for (; buf_cnt < 32; buf_cnt += 4)
1720 {
1721 cache_line[buf_cnt / 4] = 0xe1a08008;
1722 }
1723
1724 /* only load addresses other than the reset vectors */
1725 if ((address % 0x400) != 0x0)
1726 {
1727 xscale_load_ic(target, 1, address, cache_line);
1728 }
1729
1730 address += buf_cnt;
1731 binary_size -= buf_cnt;
1732 };
1733
1734 xscale_load_ic(target, 1, 0x0, xscale->low_vectors);
1735 xscale_load_ic(target, 1, 0xffff0000, xscale->high_vectors);
1736
1737 jtag_add_runtest(30, TAP_RTI);
1738
1739 jtag_add_sleep(100000);
1740
1741 /* set Hold reset, Halt mode and Trap Reset */
1742 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 30, 1, 0x1);
1743 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 16, 1, 0x1);
1744 xscale_write_dcsr(target, 1, 0);
1745
1746 /* clear Hold reset to let the target run (should enter debug handler) */
1747 xscale_write_dcsr(target, 0, 1);
1748 target->state = TARGET_RUNNING;
1749
1750 if (!target->reset_halt)
1751 {
1752 jtag_add_sleep(10000);
1753
1754 /* we should have entered debug now */
1755 xscale_debug_entry(target);
1756 target->state = TARGET_HALTED;
1757
1758 /* resume the target */
1759 xscale_resume(target, 1, 0x0, 1, 0);
1760 }
1761
1762 fileio_close(&debug_handler);
1763 }
1764 else
1765 {
1766 jtag_add_reset(0, 0);
1767 }
1768
1769
1770 return ERROR_OK;
1771 }
1772
1773 int xscale_soft_reset_halt(struct target_s *target)
1774 {
1775
1776 return ERROR_OK;
1777 }
1778
1779 int xscale_read_core_reg(struct target_s *target, int num, enum armv4_5_mode mode)
1780 {
1781
1782 return ERROR_OK;
1783 }
1784
1785 int xscale_write_core_reg(struct target_s *target, int num, enum armv4_5_mode mode, u32 value)
1786 {
1787
1788 return ERROR_OK;
1789 }
1790
1791 int xscale_full_context(target_t *target)
1792 {
1793 armv4_5_common_t *armv4_5 = target->arch_info;
1794
1795 u32 *buffer;
1796
1797 int i, j;
1798
1799 LOG_DEBUG("-");
1800
1801 if (target->state != TARGET_HALTED)
1802 {
1803 LOG_WARNING("target not halted");
1804 return ERROR_TARGET_NOT_HALTED;
1805 }
1806
1807 buffer = malloc(4 * 8);
1808
1809 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1810 * we can't enter User mode on an XScale (unpredictable),
1811 * but User shares registers with SYS
1812 */
1813 for(i = 1; i < 7; i++)
1814 {
1815 int valid = 1;
1816
1817 /* check if there are invalid registers in the current mode
1818 */
1819 for (j = 0; j <= 16; j++)
1820 {
1821 if (ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).valid == 0)
1822 valid = 0;
1823 }
1824
1825 if (!valid)
1826 {
1827 u32 tmp_cpsr;
1828
1829 /* request banked registers */
1830 xscale_send_u32(target, 0x0);
1831
1832 tmp_cpsr = 0x0;
1833 tmp_cpsr |= armv4_5_number_to_mode(i);
1834 tmp_cpsr |= 0xc0; /* I/F bits */
1835
1836 /* send CPSR for desired mode */
1837 xscale_send_u32(target, tmp_cpsr);
1838
1839 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1840 if ((armv4_5_number_to_mode(i) != ARMV4_5_MODE_USR) && (armv4_5_number_to_mode(i) != ARMV4_5_MODE_SYS))
1841 {
1842 xscale_receive(target, buffer, 8);
1843 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).value, 0, 32, buffer[7]);
1844 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), 16).dirty = 0;
1845 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), 16).valid = 1;
1846 }
1847 else
1848 {
1849 xscale_receive(target, buffer, 7);
1850 }
1851
1852 /* move data from buffer to register cache */
1853 for (j = 8; j <= 14; j++)
1854 {
1855 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).value, 0, 32, buffer[j - 8]);
1856 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).dirty = 0;
1857 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).valid = 1;
1858 }
1859 }
1860 }
1861
1862 free(buffer);
1863
1864 return ERROR_OK;
1865 }
1866
1867 int xscale_restore_context(target_t *target)
1868 {
1869 armv4_5_common_t *armv4_5 = target->arch_info;
1870
1871 int i, j;
1872
1873 LOG_DEBUG("-");
1874
1875 if (target->state != TARGET_HALTED)
1876 {
1877 LOG_WARNING("target not halted");
1878 return ERROR_TARGET_NOT_HALTED;
1879 }
1880
1881 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1882 * we can't enter User mode on an XScale (unpredictable),
1883 * but User shares registers with SYS
1884 */
1885 for(i = 1; i < 7; i++)
1886 {
1887 int dirty = 0;
1888
1889 /* check if there are invalid registers in the current mode
1890 */
1891 for (j = 8; j <= 14; j++)
1892 {
1893 if (ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).dirty == 1)
1894 dirty = 1;
1895 }
1896
1897 /* if not USR/SYS, check if the SPSR needs to be written */
1898 if ((armv4_5_number_to_mode(i) != ARMV4_5_MODE_USR) && (armv4_5_number_to_mode(i) != ARMV4_5_MODE_SYS))
1899 {
1900 if (ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), 16).dirty == 1)
1901 dirty = 1;
1902 }
1903
1904 if (dirty)
1905 {
1906 u32 tmp_cpsr;
1907
1908 /* send banked registers */
1909 xscale_send_u32(target, 0x1);
1910
1911 tmp_cpsr = 0x0;
1912 tmp_cpsr |= armv4_5_number_to_mode(i);
1913 tmp_cpsr |= 0xc0; /* I/F bits */
1914
1915 /* send CPSR for desired mode */
1916 xscale_send_u32(target, tmp_cpsr);
1917
1918 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1919 for (j = 8; j <= 14; j++)
1920 {
1921 xscale_send_u32(target, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, j).value, 0, 32));
1922 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), j).dirty = 0;
1923 }
1924
1925 if ((armv4_5_number_to_mode(i) != ARMV4_5_MODE_USR) && (armv4_5_number_to_mode(i) != ARMV4_5_MODE_SYS))
1926 {
1927 xscale_send_u32(target, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).value, 0, 32));
1928 ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5_number_to_mode(i), 16).dirty = 0;
1929 }
1930 }
1931 }
1932
1933 return ERROR_OK;
1934 }
1935
1936 int xscale_read_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer)
1937 {
1938 armv4_5_common_t *armv4_5 = target->arch_info;
1939 xscale_common_t *xscale = armv4_5->arch_info;
1940 u32 *buf32;
1941 int i;
1942 int retval;
1943
1944 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address, size, count);
1945
1946 if (target->state != TARGET_HALTED)
1947 {
1948 LOG_WARNING("target not halted");
1949 return ERROR_TARGET_NOT_HALTED;
1950 }
1951
1952 /* sanitize arguments */
1953 if (((size != 4) && (size != 2) && (size != 1)) || (count == 0) || !(buffer))
1954 return ERROR_INVALID_ARGUMENTS;
1955
1956 if (((size == 4) && (address & 0x3u)) || ((size == 2) && (address & 0x1u)))
1957 return ERROR_TARGET_UNALIGNED_ACCESS;
1958
1959 /* send memory read request (command 0x1n, n: access size) */
1960 if ((retval=xscale_send_u32(target, 0x10 | size))!=ERROR_OK)
1961 return retval;
1962
1963 /* send base address for read request */
1964 if ((retval=xscale_send_u32(target, address))!=ERROR_OK)
1965 return retval;
1966
1967 /* send number of requested data words */
1968 if ((retval=xscale_send_u32(target, count))!=ERROR_OK)
1969 return retval;
1970
1971 /* receive data from target (count times 32-bit words in host endianness) */
1972 buf32 = malloc(4 * count);
1973 if ((retval=xscale_receive(target, buf32, count))!=ERROR_OK)
1974 return retval;
1975
1976 /* extract data from host-endian buffer into byte stream */
1977 for (i = 0; i < count; i++)
1978 {
1979 switch (size)
1980 {
1981 case 4:
1982 target_buffer_set_u32(target, buffer, buf32[i]);
1983 buffer += 4;
1984 break;
1985 case 2:
1986 target_buffer_set_u16(target, buffer, buf32[i] & 0xffff);
1987 buffer += 2;
1988 break;
1989 case 1:
1990 *buffer++ = buf32[i] & 0xff;
1991 break;
1992 default:
1993 LOG_ERROR("should never get here");
1994 exit(-1);
1995 }
1996 }
1997
1998 free(buf32);
1999
2000 /* examine DCSR, to see if Sticky Abort (SA) got set */
2001 if ((retval=xscale_read_dcsr(target))!=ERROR_OK)
2002 return retval;
2003 if (buf_get_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 5, 1) == 1)
2004 {
2005 /* clear SA bit */
2006 if ((retval=xscale_send_u32(target, 0x60))!=ERROR_OK)
2007 return retval;
2008
2009 return ERROR_TARGET_DATA_ABORT;
2010 }
2011
2012 return ERROR_OK;
2013 }
2014
2015 int xscale_write_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer)
2016 {
2017 armv4_5_common_t *armv4_5 = target->arch_info;
2018 xscale_common_t *xscale = armv4_5->arch_info;
2019 int retval;
2020
2021 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address, size, count);
2022
2023 if (target->state != TARGET_HALTED)
2024 {
2025 LOG_WARNING("target not halted");
2026 return ERROR_TARGET_NOT_HALTED;
2027 }
2028
2029 /* sanitize arguments */
2030 if (((size != 4) && (size != 2) && (size != 1)) || (count == 0) || !(buffer))
2031 return ERROR_INVALID_ARGUMENTS;
2032
2033 if (((size == 4) && (address & 0x3u)) || ((size == 2) && (address & 0x1u)))
2034 return ERROR_TARGET_UNALIGNED_ACCESS;
2035
2036 /* send memory write request (command 0x2n, n: access size) */
2037 if ((retval=xscale_send_u32(target, 0x20 | size))!=ERROR_OK)
2038 return retval;
2039
2040 /* send base address for read request */
2041 if ((retval=xscale_send_u32(target, address))!=ERROR_OK)
2042 return retval;
2043
2044 /* send number of requested data words to be written*/
2045 if ((retval=xscale_send_u32(target, count))!=ERROR_OK)
2046 return retval;
2047
2048 /* extract data from host-endian buffer into byte stream */
2049 #if 0
2050 for (i = 0; i < count; i++)
2051 {
2052 switch (size)
2053 {
2054 case 4:
2055 value = target_buffer_get_u32(target, buffer);
2056 xscale_send_u32(target, value);
2057 buffer += 4;
2058 break;
2059 case 2:
2060 value = target_buffer_get_u16(target, buffer);
2061 xscale_send_u32(target, value);
2062 buffer += 2;
2063 break;
2064 case 1:
2065 value = *buffer;
2066 xscale_send_u32(target, value);
2067 buffer += 1;
2068 break;
2069 default:
2070 LOG_ERROR("should never get here");
2071 exit(-1);
2072 }
2073 }
2074 #endif
2075 if ((retval=xscale_send(target, buffer, count, size))!=ERROR_OK)
2076 return retval;
2077
2078 /* examine DCSR, to see if Sticky Abort (SA) got set */
2079 if ((retval=xscale_read_dcsr(target))!=ERROR_OK)
2080 return retval;
2081 if (buf_get_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 5, 1) == 1)
2082 {
2083 /* clear SA bit */
2084 if ((retval=xscale_send_u32(target, 0x60))!=ERROR_OK)
2085 return retval;
2086
2087 return ERROR_TARGET_DATA_ABORT;
2088 }
2089
2090 return ERROR_OK;
2091 }
2092
2093 int xscale_bulk_write_memory(target_t *target, u32 address, u32 count, u8 *buffer)
2094 {
2095 return xscale_write_memory(target, address, 4, count, buffer);
2096 }
2097
2098 u32 xscale_get_ttb(target_t *target)
2099 {
2100 armv4_5_common_t *armv4_5 = target->arch_info;
2101 xscale_common_t *xscale = armv4_5->arch_info;
2102 u32 ttb;
2103
2104 xscale_get_reg(&xscale->reg_cache->reg_list[XSCALE_TTB]);
2105 ttb = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_TTB].value, 0, 32);
2106
2107 return ttb;
2108 }
2109
2110 void xscale_disable_mmu_caches(target_t *target, int mmu, int d_u_cache, int i_cache)
2111 {
2112 armv4_5_common_t *armv4_5 = target->arch_info;
2113 xscale_common_t *xscale = armv4_5->arch_info;
2114 u32 cp15_control;
2115
2116 /* read cp15 control register */
2117 xscale_get_reg(&xscale->reg_cache->reg_list[XSCALE_CTRL]);
2118 cp15_control = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_CTRL].value, 0, 32);
2119
2120 if (mmu)
2121 cp15_control &= ~0x1U;
2122
2123 if (d_u_cache)
2124 {
2125 /* clean DCache */
2126 xscale_send_u32(target, 0x50);
2127 xscale_send_u32(target, xscale->cache_clean_address);
2128
2129 /* invalidate DCache */
2130 xscale_send_u32(target, 0x51);
2131
2132 cp15_control &= ~0x4U;
2133 }
2134
2135 if (i_cache)
2136 {
2137 /* invalidate ICache */
2138 xscale_send_u32(target, 0x52);
2139 cp15_control &= ~0x1000U;
2140 }
2141
2142 /* write new cp15 control register */
2143 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_CTRL], cp15_control);
2144
2145 /* execute cpwait to ensure outstanding operations complete */
2146 xscale_send_u32(target, 0x53);
2147 }
2148
2149 void xscale_enable_mmu_caches(target_t *target, int mmu, int d_u_cache, int i_cache)
2150 {
2151 armv4_5_common_t *armv4_5 = target->arch_info;
2152 xscale_common_t *xscale = armv4_5->arch_info;
2153 u32 cp15_control;
2154
2155 /* read cp15 control register */
2156 xscale_get_reg(&xscale->reg_cache->reg_list[XSCALE_CTRL]);
2157 cp15_control = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_CTRL].value, 0, 32);
2158
2159 if (mmu)
2160 cp15_control |= 0x1U;
2161
2162 if (d_u_cache)
2163 cp15_control |= 0x4U;
2164
2165 if (i_cache)
2166 cp15_control |= 0x1000U;
2167
2168 /* write new cp15 control register */
2169 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_CTRL], cp15_control);
2170
2171 /* execute cpwait to ensure outstanding operations complete */
2172 xscale_send_u32(target, 0x53);
2173 }
2174
2175 int xscale_set_breakpoint(struct target_s *target, breakpoint_t *breakpoint)
2176 {
2177 int retval;
2178 armv4_5_common_t *armv4_5 = target->arch_info;
2179 xscale_common_t *xscale = armv4_5->arch_info;
2180
2181 if (target->state != TARGET_HALTED)
2182 {
2183 LOG_WARNING("target not halted");
2184 return ERROR_TARGET_NOT_HALTED;
2185 }
2186
2187 if (breakpoint->set)
2188 {
2189 LOG_WARNING("breakpoint already set");
2190 return ERROR_OK;
2191 }
2192
2193 if (breakpoint->type == BKPT_HARD)
2194 {
2195 u32 value = breakpoint->address | 1;
2196 if (!xscale->ibcr0_used)
2197 {
2198 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_IBCR0], value);
2199 xscale->ibcr0_used = 1;
2200 breakpoint->set = 1; /* breakpoint set on first breakpoint register */
2201 }
2202 else if (!xscale->ibcr1_used)
2203 {
2204 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_IBCR1], value);
2205 xscale->ibcr1_used = 1;
2206 breakpoint->set = 2; /* breakpoint set on second breakpoint register */
2207 }
2208 else
2209 {
2210 LOG_ERROR("BUG: no hardware comparator available");
2211 return ERROR_OK;
2212 }
2213 }
2214 else if (breakpoint->type == BKPT_SOFT)
2215 {
2216 if (breakpoint->length == 4)
2217 {
2218 /* keep the original instruction in target endianness */
2219 if((retval = target->type->read_memory(target, breakpoint->address, 4, 1, breakpoint->orig_instr)) != ERROR_OK)
2220 {
2221 return retval;
2222 }
2223 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2224 if((retval = target_write_u32(target, breakpoint->address, xscale->arm_bkpt)) != ERROR_OK)
2225 {
2226 return retval;
2227 }
2228 }
2229 else
2230 {
2231 /* keep the original instruction in target endianness */
2232 if((retval = target->type->read_memory(target, breakpoint->address, 2, 1, breakpoint->orig_instr)) != ERROR_OK)
2233 {
2234 return retval;
2235 }
2236 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2237 if((retval = target_write_u32(target, breakpoint->address, xscale->thumb_bkpt)) != ERROR_OK)
2238 {
2239 return retval;
2240 }
2241 }
2242 breakpoint->set = 1;
2243 }
2244
2245 return ERROR_OK;
2246
2247 }
2248
2249 int xscale_add_breakpoint(struct target_s *target, breakpoint_t *breakpoint)
2250 {
2251 armv4_5_common_t *armv4_5 = target->arch_info;
2252 xscale_common_t *xscale = armv4_5->arch_info;
2253
2254 if (target->state != TARGET_HALTED)
2255 {
2256 LOG_WARNING("target not halted");
2257 return ERROR_TARGET_NOT_HALTED;
2258 }
2259
2260 if ((breakpoint->type == BKPT_HARD) && (xscale->ibcr_available < 1))
2261 {
2262 LOG_INFO("no breakpoint unit available for hardware breakpoint");
2263 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
2264 }
2265 else
2266 {
2267 xscale->ibcr_available--;
2268 }
2269
2270 if ((breakpoint->length != 2) && (breakpoint->length != 4))
2271 {
2272 LOG_INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2273 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
2274 }
2275
2276 return ERROR_OK;
2277 }
2278
2279 int xscale_unset_breakpoint(struct target_s *target, breakpoint_t *breakpoint)
2280 {
2281 int retval;
2282 armv4_5_common_t *armv4_5 = target->arch_info;
2283 xscale_common_t *xscale = armv4_5->arch_info;
2284
2285 if (target->state != TARGET_HALTED)
2286 {
2287 LOG_WARNING("target not halted");
2288 return ERROR_TARGET_NOT_HALTED;
2289 }
2290
2291 if (!breakpoint->set)
2292 {
2293 LOG_WARNING("breakpoint not set");
2294 return ERROR_OK;
2295 }
2296
2297 if (breakpoint->type == BKPT_HARD)
2298 {
2299 if (breakpoint->set == 1)
2300 {
2301 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_IBCR0], 0x0);
2302 xscale->ibcr0_used = 0;
2303 }
2304 else if (breakpoint->set == 2)
2305 {
2306 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_IBCR1], 0x0);
2307 xscale->ibcr1_used = 0;
2308 }
2309 breakpoint->set = 0;
2310 }
2311 else
2312 {
2313 /* restore original instruction (kept in target endianness) */
2314 if (breakpoint->length == 4)
2315 {
2316 if((retval = target->type->write_memory(target, breakpoint->address, 4, 1, breakpoint->orig_instr)) != ERROR_OK)
2317 {
2318 return retval;
2319 }
2320 }
2321 else
2322 {
2323 if((retval = target->type->write_memory(target, breakpoint->address, 2, 1, breakpoint->orig_instr)) != ERROR_OK)
2324 {
2325 return retval;
2326 }
2327 }
2328 breakpoint->set = 0;
2329 }
2330
2331 return ERROR_OK;
2332 }
2333
2334 int xscale_remove_breakpoint(struct target_s *target, breakpoint_t *breakpoint)
2335 {
2336 armv4_5_common_t *armv4_5 = target->arch_info;
2337 xscale_common_t *xscale = armv4_5->arch_info;
2338
2339 if (target->state != TARGET_HALTED)
2340 {
2341 LOG_WARNING("target not halted");
2342 return ERROR_TARGET_NOT_HALTED;
2343 }
2344
2345 if (breakpoint->set)
2346 {
2347 xscale_unset_breakpoint(target, breakpoint);
2348 }
2349
2350 if (breakpoint->type == BKPT_HARD)
2351 xscale->ibcr_available++;
2352
2353 return ERROR_OK;
2354 }
2355
2356 int xscale_set_watchpoint(struct target_s *target, watchpoint_t *watchpoint)
2357 {
2358 armv4_5_common_t *armv4_5 = target->arch_info;
2359 xscale_common_t *xscale = armv4_5->arch_info;
2360 u8 enable=0;
2361 reg_t *dbcon = &xscale->reg_cache->reg_list[XSCALE_DBCON];
2362 u32 dbcon_value = buf_get_u32(dbcon->value, 0, 32);
2363
2364 if (target->state != TARGET_HALTED)
2365 {
2366 LOG_WARNING("target not halted");
2367 return ERROR_TARGET_NOT_HALTED;
2368 }
2369
2370 xscale_get_reg(dbcon);
2371
2372 switch (watchpoint->rw)
2373 {
2374 case WPT_READ:
2375 enable = 0x3;
2376 break;
2377 case WPT_ACCESS:
2378 enable = 0x2;
2379 break;
2380 case WPT_WRITE:
2381 enable = 0x1;
2382 break;
2383 default:
2384 LOG_ERROR("BUG: watchpoint->rw neither read, write nor access");
2385 }
2386
2387 if (!xscale->dbr0_used)
2388 {
2389 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_DBR0], watchpoint->address);
2390 dbcon_value |= enable;
2391 xscale_set_reg_u32(dbcon, dbcon_value);
2392 watchpoint->set = 1;
2393 xscale->dbr0_used = 1;
2394 }
2395 else if (!xscale->dbr1_used)
2396 {
2397 xscale_set_reg_u32(&xscale->reg_cache->reg_list[XSCALE_DBR1], watchpoint->address);
2398 dbcon_value |= enable << 2;
2399 xscale_set_reg_u32(dbcon, dbcon_value);
2400 watchpoint->set = 2;
2401 xscale->dbr1_used = 1;
2402 }
2403 else
2404 {
2405 LOG_ERROR("BUG: no hardware comparator available");
2406 return ERROR_OK;
2407 }
2408
2409 return ERROR_OK;
2410 }
2411
2412 int xscale_add_watchpoint(struct target_s *target, watchpoint_t *watchpoint)
2413 {
2414 armv4_5_common_t *armv4_5 = target->arch_info;
2415 xscale_common_t *xscale = armv4_5->arch_info;
2416
2417 if (target->state != TARGET_HALTED)
2418 {
2419 LOG_WARNING("target not halted");
2420 return ERROR_TARGET_NOT_HALTED;
2421 }
2422
2423 if (xscale->dbr_available < 1)
2424 {
2425 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
2426 }
2427
2428 if ((watchpoint->length != 1) && (watchpoint->length != 2) && (watchpoint->length != 4))
2429 {
2430 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
2431 }
2432
2433 xscale->dbr_available--;
2434
2435 return ERROR_OK;
2436 }
2437
2438 int xscale_unset_watchpoint(struct target_s *target, watchpoint_t *watchpoint)
2439 {
2440 armv4_5_common_t *armv4_5 = target->arch_info;
2441 xscale_common_t *xscale = armv4_5->arch_info;
2442 reg_t *dbcon = &xscale->reg_cache->reg_list[XSCALE_DBCON];
2443 u32 dbcon_value = buf_get_u32(dbcon->value, 0, 32);
2444
2445 if (target->state != TARGET_HALTED)
2446 {
2447 LOG_WARNING("target not halted");
2448 return ERROR_TARGET_NOT_HALTED;
2449 }
2450
2451 if (!watchpoint->set)
2452 {
2453 LOG_WARNING("breakpoint not set");
2454 return ERROR_OK;
2455 }
2456
2457 if (watchpoint->set == 1)
2458 {
2459 dbcon_value &= ~0x3;
2460 xscale_set_reg_u32(dbcon, dbcon_value);
2461 xscale->dbr0_used = 0;
2462 }
2463 else if (watchpoint->set == 2)
2464 {
2465 dbcon_value &= ~0xc;
2466 xscale_set_reg_u32(dbcon, dbcon_value);
2467 xscale->dbr1_used = 0;
2468 }
2469 watchpoint->set = 0;
2470
2471 return ERROR_OK;
2472 }
2473
2474 int xscale_remove_watchpoint(struct target_s *target, watchpoint_t *watchpoint)
2475 {
2476 armv4_5_common_t *armv4_5 = target->arch_info;
2477 xscale_common_t *xscale = armv4_5->arch_info;
2478
2479 if (target->state != TARGET_HALTED)
2480 {
2481 LOG_WARNING("target not halted");
2482 return ERROR_TARGET_NOT_HALTED;
2483 }
2484
2485 if (watchpoint->set)
2486 {
2487 xscale_unset_watchpoint(target, watchpoint);
2488 }
2489
2490 xscale->dbr_available++;
2491
2492 return ERROR_OK;
2493 }
2494
2495 void xscale_enable_watchpoints(struct target_s *target)
2496 {
2497 watchpoint_t *watchpoint = target->watchpoints;
2498
2499 while (watchpoint)
2500 {
2501 if (watchpoint->set == 0)
2502 xscale_set_watchpoint(target, watchpoint);
2503 watchpoint = watchpoint->next;
2504 }
2505 }
2506
2507 void xscale_enable_breakpoints(struct target_s *target)
2508 {
2509 breakpoint_t *breakpoint = target->breakpoints;
2510
2511 /* set any pending breakpoints */
2512 while (breakpoint)
2513 {
2514 if (breakpoint->set == 0)
2515 xscale_set_breakpoint(target, breakpoint);
2516 breakpoint = breakpoint->next;
2517 }
2518 }
2519
2520 int xscale_get_reg(reg_t *reg)
2521 {
2522 xscale_reg_t *arch_info = reg->arch_info;
2523 target_t *target = arch_info->target;
2524 armv4_5_common_t *armv4_5 = target->arch_info;
2525 xscale_common_t *xscale = armv4_5->arch_info;
2526
2527 /* DCSR, TX and RX are accessible via JTAG */
2528 if (strcmp(reg->name, "XSCALE_DCSR") == 0)
2529 {
2530 return xscale_read_dcsr(arch_info->target);
2531 }
2532 else if (strcmp(reg->name, "XSCALE_TX") == 0)
2533 {
2534 /* 1 = consume register content */
2535 return xscale_read_tx(arch_info->target, 1);
2536 }
2537 else if (strcmp(reg->name, "XSCALE_RX") == 0)
2538 {
2539 /* can't read from RX register (host -> debug handler) */
2540 return ERROR_OK;
2541 }
2542 else if (strcmp(reg->name, "XSCALE_TXRXCTRL") == 0)
2543 {
2544 /* can't (explicitly) read from TXRXCTRL register */
2545 return ERROR_OK;
2546 }
2547 else /* Other DBG registers have to be transfered by the debug handler */
2548 {
2549 /* send CP read request (command 0x40) */
2550 xscale_send_u32(target, 0x40);
2551
2552 /* send CP register number */
2553 xscale_send_u32(target, arch_info->dbg_handler_number);
2554
2555 /* read register value */
2556 xscale_read_tx(target, 1);
2557 buf_cpy(xscale->reg_cache->reg_list[XSCALE_TX].value, reg->value, 32);
2558
2559 reg->dirty = 0;
2560 reg->valid = 1;
2561 }
2562
2563 return ERROR_OK;
2564 }
2565
2566 int xscale_set_reg(reg_t *reg, u8* buf)
2567 {
2568 xscale_reg_t *arch_info = reg->arch_info;
2569 target_t *target = arch_info->target;
2570 armv4_5_common_t *armv4_5 = target->arch_info;
2571 xscale_common_t *xscale = armv4_5->arch_info;
2572 u32 value = buf_get_u32(buf, 0, 32);
2573
2574 /* DCSR, TX and RX are accessible via JTAG */
2575 if (strcmp(reg->name, "XSCALE_DCSR") == 0)
2576 {
2577 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 0, 32, value);
2578 return xscale_write_dcsr(arch_info->target, -1, -1);
2579 }
2580 else if (strcmp(reg->name, "XSCALE_RX") == 0)
2581 {
2582 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_RX].value, 0, 32, value);
2583 return xscale_write_rx(arch_info->target);
2584 }
2585 else if (strcmp(reg->name, "XSCALE_TX") == 0)
2586 {
2587 /* can't write to TX register (debug-handler -> host) */
2588 return ERROR_OK;
2589 }
2590 else if (strcmp(reg->name, "XSCALE_TXRXCTRL") == 0)
2591 {
2592 /* can't (explicitly) write to TXRXCTRL register */
2593 return ERROR_OK;
2594 }
2595 else /* Other DBG registers have to be transfered by the debug handler */
2596 {
2597 /* send CP write request (command 0x41) */
2598 xscale_send_u32(target, 0x41);
2599
2600 /* send CP register number */
2601 xscale_send_u32(target, arch_info->dbg_handler_number);
2602
2603 /* send CP register value */
2604 xscale_send_u32(target, value);
2605 buf_set_u32(reg->value, 0, 32, value);
2606 }
2607
2608 return ERROR_OK;
2609 }
2610
2611 /* convenience wrapper to access XScale specific registers */
2612 int xscale_set_reg_u32(reg_t *reg, u32 value)
2613 {
2614 u8 buf[4];
2615
2616 buf_set_u32(buf, 0, 32, value);
2617
2618 return xscale_set_reg(reg, buf);
2619 }
2620
2621 int xscale_write_dcsr_sw(target_t *target, u32 value)
2622 {
2623 /* get pointers to arch-specific information */
2624 armv4_5_common_t *armv4_5 = target->arch_info;
2625 xscale_common_t *xscale = armv4_5->arch_info;
2626 reg_t *dcsr = &xscale->reg_cache->reg_list[XSCALE_DCSR];
2627 xscale_reg_t *dcsr_arch_info = dcsr->arch_info;
2628
2629 /* send CP write request (command 0x41) */
2630 xscale_send_u32(target, 0x41);
2631
2632 /* send CP register number */
2633 xscale_send_u32(target, dcsr_arch_info->dbg_handler_number);
2634
2635 /* send CP register value */
2636 xscale_send_u32(target, value);
2637 buf_set_u32(dcsr->value, 0, 32, value);
2638
2639 return ERROR_OK;
2640 }
2641
2642 int xscale_read_trace(target_t *target)
2643 {
2644 /* get pointers to arch-specific information */
2645 armv4_5_common_t *armv4_5 = target->arch_info;
2646 xscale_common_t *xscale = armv4_5->arch_info;
2647 xscale_trace_data_t **trace_data_p;
2648
2649 /* 258 words from debug handler
2650 * 256 trace buffer entries
2651 * 2 checkpoint addresses
2652 */
2653 u32 trace_buffer[258];
2654 int is_address[256];
2655 int i, j;
2656
2657 if (target->state != TARGET_HALTED)
2658 {
2659 LOG_WARNING("target must be stopped to read trace data");
2660 return ERROR_TARGET_NOT_HALTED;
2661 }
2662
2663 /* send read trace buffer command (command 0x61) */
2664 xscale_send_u32(target, 0x61);
2665
2666 /* receive trace buffer content */
2667 xscale_receive(target, trace_buffer, 258);
2668
2669 /* parse buffer backwards to identify address entries */
2670 for (i = 255; i >= 0; i--)
2671 {
2672 is_address[i] = 0;
2673 if (((trace_buffer[i] & 0xf0) == 0x90) ||
2674 ((trace_buffer[i] & 0xf0) == 0xd0))
2675 {
2676 if (i >= 3)
2677 is_address[--i] = 1;
2678 if (i >= 2)
2679 is_address[--i] = 1;
2680 if (i >= 1)
2681 is_address[--i] = 1;
2682 if (i >= 0)
2683 is_address[--i] = 1;
2684 }
2685 }
2686
2687
2688 /* search first non-zero entry */
2689 for (j = 0; (j < 256) && (trace_buffer[j] == 0) && (!is_address[j]); j++)
2690 ;
2691
2692 if (j == 256)
2693 {
2694 LOG_DEBUG("no trace data collected");
2695 return ERROR_XSCALE_NO_TRACE_DATA;
2696 }
2697
2698 for (trace_data_p = &xscale->trace.data; *trace_data_p; trace_data_p = &(*trace_data_p)->next)
2699 ;
2700
2701 *trace_data_p = malloc(sizeof(xscale_trace_data_t));
2702 (*trace_data_p)->next = NULL;
2703 (*trace_data_p)->chkpt0 = trace_buffer[256];
2704 (*trace_data_p)->chkpt1 = trace_buffer[257];
2705 (*trace_data_p)->last_instruction = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
2706 (*trace_data_p)->entries = malloc(sizeof(xscale_trace_entry_t) * (256 - j));
2707 (*trace_data_p)->depth = 256 - j;
2708
2709 for (i = j; i < 256; i++)
2710 {
2711 (*trace_data_p)->entries[i - j].data = trace_buffer[i];
2712 if (is_address[i])
2713 (*trace_data_p)->entries[i - j].type = XSCALE_TRACE_ADDRESS;
2714 else
2715 (*trace_data_p)->entries[i - j].type = XSCALE_TRACE_MESSAGE;
2716 }
2717
2718 return ERROR_OK;
2719 }
2720
2721 int xscale_read_instruction(target_t *target, arm_instruction_t *instruction)
2722 {
2723 /* get pointers to arch-specific information */
2724 armv4_5_common_t *armv4_5 = target->arch_info;
2725 xscale_common_t *xscale = armv4_5->arch_info;
2726 int i;
2727 int section = -1;
2728 u32 size_read;
2729 u32 opcode;
2730 int retval;
2731
2732 if (!xscale->trace.image)
2733 return ERROR_TRACE_IMAGE_UNAVAILABLE;
2734
2735 /* search for the section the current instruction belongs to */
2736 for (i = 0; i < xscale->trace.image->num_sections; i++)
2737 {
2738 if ((xscale->trace.image->sections[i].base_address <= xscale->trace.current_pc) &&
2739 (xscale->trace.image->sections[i].base_address + xscale->trace.image->sections[i].size > xscale->trace.current_pc))
2740 {
2741 section = i;
2742 break;
2743 }
2744 }
2745
2746 if (section == -1)
2747 {
2748 /* current instruction couldn't be found in the image */
2749 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE;
2750 }
2751
2752 if (xscale->trace.core_state == ARMV4_5_STATE_ARM)
2753 {
2754 u8 buf[4];
2755 if ((retval = image_read_section(xscale->trace.image, section,
2756 xscale->trace.current_pc - xscale->trace.image->sections[section].base_address,
2757 4, buf, &size_read)) != ERROR_OK)
2758 {
2759 LOG_ERROR("error while reading instruction: %i", retval);
2760 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE;
2761 }
2762 opcode = target_buffer_get_u32(target, buf);
2763 arm_evaluate_opcode(opcode, xscale->trace.current_pc, instruction);
2764 }
2765 else if (xscale->trace.core_state == ARMV4_5_STATE_THUMB)
2766 {
2767 u8 buf[2];
2768 if ((retval = image_read_section(xscale->trace.image, section,
2769 xscale->trace.current_pc - xscale->trace.image->sections[section].base_address,
2770 2, buf, &size_read)) != ERROR_OK)
2771 {
2772 LOG_ERROR("error while reading instruction: %i", retval);
2773 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE;
2774 }
2775 opcode = target_buffer_get_u16(target, buf);
2776 thumb_evaluate_opcode(opcode, xscale->trace.current_pc, instruction);
2777 }
2778 else
2779 {
2780 LOG_ERROR("BUG: unknown core state encountered");
2781 exit(-1);
2782 }
2783
2784 return ERROR_OK;
2785 }
2786
2787 int xscale_branch_address(xscale_trace_data_t *trace_data, int i, u32 *target)
2788 {
2789 /* if there are less than four entries prior to the indirect branch message
2790 * we can't extract the address */
2791 if (i < 4)
2792 {
2793 return -1;
2794 }
2795
2796 *target = (trace_data->entries[i-1].data) | (trace_data->entries[i-2].data << 8) |
2797 (trace_data->entries[i-3].data << 16) | (trace_data->entries[i-4].data << 24);
2798
2799 return 0;
2800 }
2801
2802 int xscale_analyze_trace(target_t *target, command_context_t *cmd_ctx)
2803 {
2804 /* get pointers to arch-specific information */
2805 armv4_5_common_t *armv4_5 = target->arch_info;
2806 xscale_common_t *xscale = armv4_5->arch_info;
2807 int next_pc_ok = 0;
2808 u32 next_pc = 0x0;
2809 xscale_trace_data_t *trace_data = xscale->trace.data;
2810 int retval;
2811
2812 while (trace_data)
2813 {
2814 int i, chkpt;
2815 int rollover;
2816 int branch;
2817 int exception;
2818 xscale->trace.core_state = ARMV4_5_STATE_ARM;
2819
2820 chkpt = 0;
2821 rollover = 0;
2822
2823 for (i = 0; i < trace_data->depth; i++)
2824 {
2825 next_pc_ok = 0;
2826 branch = 0;
2827 exception = 0;
2828
2829 if (trace_data->entries[i].type == XSCALE_TRACE_ADDRESS)
2830 continue;
2831
2832 switch ((trace_data->entries[i].data & 0xf0) >> 4)
2833 {
2834 case 0: /* Exceptions */
2835 case 1:
2836 case 2:
2837 case 3:
2838 case 4:
2839 case 5:
2840 case 6:
2841 case 7:
2842 exception = (trace_data->entries[i].data & 0x70) >> 4;
2843 next_pc_ok = 1;
2844 next_pc = (trace_data->entries[i].data & 0xf0) >> 2;
2845 command_print(cmd_ctx, "--- exception %i ---", (trace_data->entries[i].data & 0xf0) >> 4);
2846 break;
2847 case 8: /* Direct Branch */
2848 branch = 1;
2849 break;
2850 case 9: /* Indirect Branch */
2851 branch = 1;
2852 if (xscale_branch_address(trace_data, i, &next_pc) == 0)
2853 {
2854 next_pc_ok = 1;
2855 }
2856 break;
2857 case 13: /* Checkpointed Indirect Branch */
2858 if (xscale_branch_address(trace_data, i, &next_pc) == 0)
2859 {
2860 next_pc_ok = 1;
2861 if (((chkpt == 0) && (next_pc != trace_data->chkpt0))
2862 || ((chkpt == 1) && (next_pc != trace_data->chkpt1)))
2863 LOG_WARNING("checkpointed indirect branch target address doesn't match checkpoint");
2864 }
2865 /* explicit fall-through */
2866 case 12: /* Checkpointed Direct Branch */
2867 branch = 1;
2868 if (chkpt == 0)
2869 {
2870 next_pc_ok = 1;
2871 next_pc = trace_data->chkpt0;
2872 chkpt++;
2873 }
2874 else if (chkpt == 1)
2875 {
2876 next_pc_ok = 1;
2877 next_pc = trace_data->chkpt0;
2878 chkpt++;
2879 }
2880 else
2881 {
2882 LOG_WARNING("more than two checkpointed branches encountered");
2883 }
2884 break;
2885 case 15: /* Roll-over */
2886 rollover++;
2887 continue;
2888 default: /* Reserved */
2889 command_print(cmd_ctx, "--- reserved trace message ---");
2890 LOG_ERROR("BUG: trace message %i is reserved", (trace_data->entries[i].data & 0xf0) >> 4);
2891 return ERROR_OK;
2892 }
2893
2894 if (xscale->trace.pc_ok)
2895 {
2896 int executed = (trace_data->entries[i].data & 0xf) + rollover * 16;
2897 arm_instruction_t instruction;
2898
2899 if ((exception == 6) || (exception == 7))
2900 {
2901 /* IRQ or FIQ exception, no instruction executed */
2902 executed -= 1;
2903 }
2904
2905 while (executed-- >= 0)
2906 {
2907 if ((retval = xscale_read_instruction(target, &instruction)) != ERROR_OK)
2908 {
2909 /* can't continue tracing with no image available */
2910 if (retval == ERROR_TRACE_IMAGE_UNAVAILABLE)
2911 {
2912 return retval;
2913 }
2914 else if (retval == ERROR_TRACE_INSTRUCTION_UNAVAILABLE)
2915 {
2916 /* TODO: handle incomplete images */
2917 }
2918 }
2919
2920 /* a precise abort on a load to the PC is included in the incremental
2921 * word count, other instructions causing data aborts are not included
2922 */
2923 if ((executed == 0) && (exception == 4)
2924 && ((instruction.type >= ARM_LDR) && (instruction.type <= ARM_LDM)))
2925 {
2926 if ((instruction.type == ARM_LDM)
2927 && ((instruction.info.load_store_multiple.register_list & 0x8000) == 0))
2928 {
2929 executed--;
2930 }
2931 else if (((instruction.type >= ARM_LDR) && (instruction.type <= ARM_LDRSH))
2932 && (instruction.info.load_store.Rd != 15))
2933 {
2934 executed--;
2935 }
2936 }
2937
2938 /* only the last instruction executed
2939 * (the one that caused the control flow change)
2940 * could be a taken branch
2941 */
2942 if (((executed == -1) && (branch == 1)) &&
2943 (((instruction.type == ARM_B) ||
2944 (instruction.type == ARM_BL) ||
2945 (instruction.type == ARM_BLX)) &&
2946 (instruction.info.b_bl_bx_blx.target_address != -1)))
2947 {
2948 xscale->trace.current_pc = instruction.info.b_bl_bx_blx.target_address;
2949 }
2950 else
2951 {
2952 xscale->trace.current_pc += (xscale->trace.core_state == ARMV4_5_STATE_ARM) ? 4 : 2;
2953 }
2954 command_print(cmd_ctx, "%s", instruction.text);
2955 }
2956
2957 rollover = 0;
2958 }
2959
2960 if (next_pc_ok)
2961 {
2962 xscale->trace.current_pc = next_pc;
2963 xscale->trace.pc_ok = 1;
2964 }
2965 }
2966
2967 for (; xscale->trace.current_pc < trace_data->last_instruction; xscale->trace.current_pc += (xscale->trace.core_state == ARMV4_5_STATE_ARM) ? 4 : 2)
2968 {
2969 arm_instruction_t instruction;
2970 if ((retval = xscale_read_instruction(target, &instruction)) != ERROR_OK)
2971 {
2972 /* can't continue tracing with no image available */
2973 if (retval == ERROR_TRACE_IMAGE_UNAVAILABLE)
2974 {
2975 return retval;
2976 }
2977 else if (retval == ERROR_TRACE_INSTRUCTION_UNAVAILABLE)
2978 {
2979 /* TODO: handle incomplete images */
2980 }
2981 }
2982 command_print(cmd_ctx, "%s", instruction.text);
2983 }
2984
2985 trace_data = trace_data->next;
2986 }
2987
2988 return ERROR_OK;
2989 }
2990
2991 void xscale_build_reg_cache(target_t *target)
2992 {
2993 /* get pointers to arch-specific information */
2994 armv4_5_common_t *armv4_5 = target->arch_info;
2995 xscale_common_t *xscale = armv4_5->arch_info;
2996
2997 reg_cache_t **cache_p = register_get_last_cache_p(&target->reg_cache);
2998 xscale_reg_t *arch_info = malloc(sizeof(xscale_reg_arch_info));
2999 int i;
3000 int num_regs = sizeof(xscale_reg_arch_info) / sizeof(xscale_reg_t);
3001
3002 (*cache_p) = armv4_5_build_reg_cache(target, armv4_5);
3003 armv4_5->core_cache = (*cache_p);
3004
3005 /* register a register arch-type for XScale dbg registers only once */
3006 if (xscale_reg_arch_type == -1)
3007 xscale_reg_arch_type = register_reg_arch_type(xscale_get_reg, xscale_set_reg);
3008
3009 (*cache_p)->next = malloc(sizeof(reg_cache_t));
3010 cache_p = &(*cache_p)->next;
3011
3012 /* fill in values for the xscale reg cache */
3013 (*cache_p)->name = "XScale registers";
3014 (*cache_p)->next = NULL;
3015 (*cache_p)->reg_list = malloc(num_regs * sizeof(reg_t));
3016 (*cache_p)->num_regs = num_regs;
3017
3018 for (i = 0; i < num_regs; i++)
3019 {
3020 (*cache_p)->reg_list[i].name = xscale_reg_list[i];
3021 (*cache_p)->reg_list[i].value = calloc(4, 1);
3022 (*cache_p)->reg_list[i].dirty = 0;
3023 (*cache_p)->reg_list[i].valid = 0;
3024 (*cache_p)->reg_list[i].size = 32;
3025 (*cache_p)->reg_list[i].bitfield_desc = NULL;
3026 (*cache_p)->reg_list[i].num_bitfields = 0;
3027 (*cache_p)->reg_list[i].arch_info = &arch_info[i];
3028 (*cache_p)->reg_list[i].arch_type = xscale_reg_arch_type;
3029 arch_info[i] = xscale_reg_arch_info[i];
3030 arch_info[i].target = target;
3031 }
3032
3033 xscale->reg_cache = (*cache_p);
3034 }
3035
3036 int xscale_init_target(struct command_context_s *cmd_ctx, struct target_s *target)
3037 {
3038 return ERROR_OK;
3039 }
3040
3041 int xscale_quit(void)
3042 {
3043
3044 return ERROR_OK;
3045 }
3046
3047 int xscale_init_arch_info(target_t *target, xscale_common_t *xscale, jtag_tap_t *tap, const char *variant)
3048 {
3049 armv4_5_common_t *armv4_5;
3050 u32 high_reset_branch, low_reset_branch;
3051 int i;
3052
3053 armv4_5 = &xscale->armv4_5_common;
3054
3055 /* store architecture specfic data (none so far) */
3056 xscale->arch_info = NULL;
3057 xscale->common_magic = XSCALE_COMMON_MAGIC;
3058
3059 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
3060 xscale->variant = strdup(variant);
3061
3062 /* prepare JTAG information for the new target */
3063 xscale->jtag_info.tap = tap;
3064
3065 xscale->jtag_info.dbgrx = 0x02;
3066 xscale->jtag_info.dbgtx = 0x10;
3067 xscale->jtag_info.dcsr = 0x09;
3068 xscale->jtag_info.ldic = 0x07;
3069
3070 if ((strcmp(xscale->variant, "pxa250") == 0) ||
3071 (strcmp(xscale->variant, "pxa255") == 0) ||
3072 (strcmp(xscale->variant, "pxa26x") == 0))
3073 {
3074 xscale->jtag_info.ir_length = 5;
3075 }
3076 else if ((strcmp(xscale->variant, "pxa27x") == 0) ||
3077 (strcmp(xscale->variant, "ixp42x") == 0) ||
3078 (strcmp(xscale->variant, "ixp45x") == 0) ||
3079 (strcmp(xscale->variant, "ixp46x") == 0))
3080 {
3081 xscale->jtag_info.ir_length = 7;
3082 }
3083
3084 /* the debug handler isn't installed (and thus not running) at this time */
3085 xscale->handler_installed = 0;
3086 xscale->handler_running = 0;
3087 xscale->handler_address = 0xfe000800;
3088
3089 /* clear the vectors we keep locally for reference */
3090 memset(xscale->low_vectors, 0, sizeof(xscale->low_vectors));
3091 memset(xscale->high_vectors, 0, sizeof(xscale->high_vectors));
3092
3093 /* no user-specified vectors have been configured yet */
3094 xscale->static_low_vectors_set = 0x0;
3095 xscale->static_high_vectors_set = 0x0;
3096
3097 /* calculate branches to debug handler */
3098 low_reset_branch = (xscale->handler_address + 0x20 - 0x0 - 0x8) >> 2;
3099 high_reset_branch = (xscale->handler_address + 0x20 - 0xffff0000 - 0x8) >> 2;
3100
3101 xscale->low_vectors[0] = ARMV4_5_B((low_reset_branch & 0xffffff), 0);
3102 xscale->high_vectors[0] = ARMV4_5_B((high_reset_branch & 0xffffff), 0);
3103
3104 for (i = 1; i <= 7; i++)
3105 {
3106 xscale->low_vectors[i] = ARMV4_5_B(0xfffffe, 0);
3107 xscale->high_vectors[i] = ARMV4_5_B(0xfffffe, 0);
3108 }
3109
3110 /* 64kB aligned region used for DCache cleaning */
3111 xscale->cache_clean_address = 0xfffe0000;
3112
3113 xscale->hold_rst = 0;
3114 xscale->external_debug_break = 0;
3115
3116 xscale->ibcr_available = 2;
3117 xscale->ibcr0_used = 0;
3118 xscale->ibcr1_used = 0;
3119
3120 xscale->dbr_available = 2;
3121 xscale->dbr0_used = 0;
3122 xscale->dbr1_used = 0;
3123
3124 xscale->arm_bkpt = ARMV5_BKPT(0x0);
3125 xscale->thumb_bkpt = ARMV5_T_BKPT(0x0) & 0xffff;
3126
3127 xscale->vector_catch = 0x1;
3128
3129 xscale->trace.capture_status = TRACE_IDLE;
3130 xscale->trace.data = NULL;
3131 xscale->trace.image = NULL;
3132 xscale->trace.buffer_enabled = 0;
3133 xscale->trace.buffer_fill = 0;
3134
3135 /* prepare ARMv4/5 specific information */
3136 armv4_5->arch_info = xscale;
3137 armv4_5->read_core_reg = xscale_read_core_reg;
3138 armv4_5->write_core_reg = xscale_write_core_reg;
3139 armv4_5->full_context = xscale_full_context;
3140
3141 armv4_5_init_arch_info(target, armv4_5);
3142
3143 xscale->armv4_5_mmu.armv4_5_cache.ctype = -1;
3144 xscale->armv4_5_mmu.get_ttb = xscale_get_ttb;
3145 xscale->armv4_5_mmu.read_memory = xscale_read_memory;
3146 xscale->armv4_5_mmu.write_memory = xscale_write_memory;
3147 xscale->armv4_5_mmu.disable_mmu_caches = xscale_disable_mmu_caches;
3148 xscale->armv4_5_mmu.enable_mmu_caches = xscale_enable_mmu_caches;
3149 xscale->armv4_5_mmu.has_tiny_pages = 1;
3150 xscale->armv4_5_mmu.mmu_enabled = 0;
3151
3152 return ERROR_OK;
3153 }
3154
3155 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
3156 int xscale_target_create(struct target_s *target, Jim_Interp *interp)
3157 {
3158 xscale_common_t *xscale = calloc(1,sizeof(xscale_common_t));
3159
3160 xscale_init_arch_info(target, xscale, target->tap, target->variant);
3161 xscale_build_reg_cache(target);
3162
3163 return ERROR_OK;
3164 }
3165
3166 int xscale_handle_debug_handler_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3167 {
3168 target_t *target = NULL;
3169 armv4_5_common_t *armv4_5;
3170 xscale_common_t *xscale;
3171
3172 u32 handler_address;
3173
3174 if (argc < 2)
3175 {
3176 LOG_ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
3177 return ERROR_OK;
3178 }
3179
3180 if ((target = get_target_by_num(strtoul(args[0], NULL, 0))) == NULL)
3181 {
3182 LOG_ERROR("no target '%s' configured", args[0]);
3183 return ERROR_FAIL;
3184 }
3185
3186 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3187 {
3188 return ERROR_FAIL;
3189 }
3190
3191 handler_address = strtoul(args[1], NULL, 0);
3192
3193 if (((handler_address >= 0x800) && (handler_address <= 0x1fef800)) ||
3194 ((handler_address >= 0xfe000800) && (handler_address <= 0xfffff800)))
3195 {
3196 xscale->handler_address = handler_address;
3197 }
3198 else
3199 {
3200 LOG_ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
3201 return ERROR_FAIL;
3202 }
3203
3204 return ERROR_OK;
3205 }
3206
3207 int xscale_handle_cache_clean_address_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3208 {
3209 target_t *target = NULL;
3210 armv4_5_common_t *armv4_5;
3211 xscale_common_t *xscale;
3212
3213 u32 cache_clean_address;
3214
3215 if (argc < 2)
3216 {
3217 return ERROR_COMMAND_SYNTAX_ERROR;
3218 }
3219
3220 if ((target = get_target_by_num(strtoul(args[0], NULL, 0))) == NULL)
3221 {
3222 LOG_ERROR("no target '%s' configured", args[0]);
3223 return ERROR_FAIL;
3224 }
3225
3226 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3227 {
3228 return ERROR_FAIL;
3229 }
3230
3231 cache_clean_address = strtoul(args[1], NULL, 0);
3232
3233 if (cache_clean_address & 0xffff)
3234 {
3235 LOG_ERROR("xscale cache_clean_address <address> must be 64kb aligned");
3236 }
3237 else
3238 {
3239 xscale->cache_clean_address = cache_clean_address;
3240 }
3241
3242 return ERROR_OK;
3243 }
3244
3245 int xscale_handle_cache_info_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3246 {
3247 target_t *target = get_current_target(cmd_ctx);
3248 armv4_5_common_t *armv4_5;
3249 xscale_common_t *xscale;
3250
3251 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3252 {
3253 return ERROR_OK;
3254 }
3255
3256 return armv4_5_handle_cache_info_command(cmd_ctx, &xscale->armv4_5_mmu.armv4_5_cache);
3257 }
3258
3259 static int xscale_virt2phys(struct target_s *target, u32 virtual, u32 *physical)
3260 {
3261 armv4_5_common_t *armv4_5;
3262 xscale_common_t *xscale;
3263 int retval;
3264 int type;
3265 u32 cb;
3266 int domain;
3267 u32 ap;
3268
3269
3270 if ((retval = xscale_get_arch_pointers(target, &armv4_5, &xscale)) != ERROR_OK)
3271 {
3272 return retval;
3273 }
3274 u32 ret = armv4_5_mmu_translate_va(target, &xscale->armv4_5_mmu, virtual, &type, &cb, &domain, &ap);
3275 if (type == -1)
3276 {
3277 return ret;
3278 }
3279 *physical = ret;
3280 return ERROR_OK;
3281 }
3282
3283 static int xscale_mmu(struct target_s *target, int *enabled)
3284 {
3285 armv4_5_common_t *armv4_5 = target->arch_info;
3286 xscale_common_t *xscale = armv4_5->arch_info;
3287
3288 if (target->state != TARGET_HALTED)
3289 {
3290 LOG_ERROR("Target not halted");
3291 return ERROR_TARGET_INVALID;
3292 }
3293 *enabled = xscale->armv4_5_mmu.mmu_enabled;
3294 return ERROR_OK;
3295 }
3296
3297
3298 int xscale_handle_mmu_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
3299 {
3300 target_t *target = get_current_target(cmd_ctx);
3301 armv4_5_common_t *armv4_5;
3302 xscale_common_t *xscale;
3303
3304 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3305 {
3306 return ERROR_OK;
3307 }
3308
3309 if (target->state != TARGET_HALTED)
3310 {
3311 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
3312 return ERROR_OK;
3313 }
3314
3315 if (argc >= 1)
3316 {
3317 if (strcmp("enable", args[0]) == 0)
3318 {
3319 xscale_enable_mmu_caches(target, 1, 0, 0);
3320 xscale->armv4_5_mmu.mmu_enabled = 1;
3321 }
3322 else if (strcmp("disable", args[0]) == 0)
3323 {
3324 xscale_disable_mmu_caches(target, 1, 0, 0);
3325 xscale->armv4_5_mmu.mmu_enabled = 0;
3326 }
3327 }
3328
3329 command_print(cmd_ctx, "mmu %s", (xscale->armv4_5_mmu.mmu_enabled) ? "enabled" : "disabled");
3330
3331 return ERROR_OK;
3332 }
3333
3334 int xscale_handle_idcache_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
3335 {
3336 target_t *target = get_current_target(cmd_ctx);
3337 armv4_5_common_t *armv4_5;
3338 xscale_common_t *xscale;
3339 int icache = 0, dcache = 0;
3340
3341 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3342 {
3343 return ERROR_OK;
3344 }
3345
3346 if (target->state != TARGET_HALTED)
3347 {
3348 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
3349 return ERROR_OK;
3350 }
3351
3352 if (strcmp(cmd, "icache") == 0)
3353 icache = 1;
3354 else if (strcmp(cmd, "dcache") == 0)
3355 dcache = 1;
3356
3357 if (argc >= 1)
3358 {
3359 if (strcmp("enable", args[0]) == 0)
3360 {
3361 xscale_enable_mmu_caches(target, 0, dcache, icache);
3362
3363 if (icache)
3364 xscale->armv4_5_mmu.armv4_5_cache.i_cache_enabled = 1;
3365 else if (dcache)
3366 xscale->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled = 1;
3367 }
3368 else if (strcmp("disable", args[0]) == 0)
3369 {
3370 xscale_disable_mmu_caches(target, 0, dcache, icache);
3371
3372 if (icache)
3373 xscale->armv4_5_mmu.armv4_5_cache.i_cache_enabled = 0;
3374 else if (dcache)
3375 xscale->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled = 0;
3376 }
3377 }
3378
3379 if (icache)
3380 command_print(cmd_ctx, "icache %s", (xscale->armv4_5_mmu.armv4_5_cache.i_cache_enabled) ? "enabled" : "disabled");
3381
3382 if (dcache)
3383 command_print(cmd_ctx, "dcache %s", (xscale->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled) ? "enabled" : "disabled");
3384
3385 return ERROR_OK;
3386 }
3387
3388 int xscale_handle_vector_catch_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
3389 {
3390 target_t *target = get_current_target(cmd_ctx);
3391 armv4_5_common_t *armv4_5;
3392 xscale_common_t *xscale;
3393
3394 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3395 {
3396 return ERROR_OK;
3397 }
3398
3399 if (argc < 1)
3400 {
3401 command_print(cmd_ctx, "usage: xscale vector_catch [mask]");
3402 }
3403 else
3404 {
3405 xscale->vector_catch = strtoul(args[0], NULL, 0);
3406 buf_set_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 16, 8, xscale->vector_catch);
3407 xscale_write_dcsr(target, -1, -1);
3408 }
3409
3410 command_print(cmd_ctx, "vector catch mask: 0x%2.2x", xscale->vector_catch);
3411
3412 return ERROR_OK;
3413 }
3414
3415
3416 int xscale_handle_trace_buffer_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3417 {
3418 target_t *target = get_current_target(cmd_ctx);
3419 armv4_5_common_t *armv4_5;
3420 xscale_common_t *xscale;
3421 u32 dcsr_value;
3422
3423 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3424 {
3425 return ERROR_OK;
3426 }
3427
3428 if (target->state != TARGET_HALTED)
3429 {
3430 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
3431 return ERROR_OK;
3432 }
3433
3434 if ((argc >= 1) && (strcmp("enable", args[0]) == 0))
3435 {
3436 xscale_trace_data_t *td, *next_td;
3437 xscale->trace.buffer_enabled = 1;
3438
3439 /* free old trace data */
3440 td = xscale->trace.data;
3441 while (td)
3442 {
3443 next_td = td->next;
3444
3445 if (td->entries)
3446 free(td->entries);
3447 free(td);
3448 td = next_td;
3449 }
3450 xscale->trace.data = NULL;
3451 }
3452 else if ((argc >= 1) && (strcmp("disable", args[0]) == 0))
3453 {
3454 xscale->trace.buffer_enabled = 0;
3455 }
3456
3457 if ((argc >= 2) && (strcmp("fill", args[1]) == 0))
3458 {
3459 if (argc >= 3)
3460 xscale->trace.buffer_fill = strtoul(args[2], NULL, 0);
3461 else
3462 xscale->trace.buffer_fill = 1;
3463 }
3464 else if ((argc >= 2) && (strcmp("wrap", args[1]) == 0))
3465 {
3466 xscale->trace.buffer_fill = -1;
3467 }
3468
3469 if (xscale->trace.buffer_enabled)
3470 {
3471 /* if we enable the trace buffer in fill-once
3472 * mode we know the address of the first instruction */
3473 xscale->trace.pc_ok = 1;
3474 xscale->trace.current_pc = buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32);
3475 }
3476 else
3477 {
3478 /* otherwise the address is unknown, and we have no known good PC */
3479 xscale->trace.pc_ok = 0;
3480 }
3481
3482 command_print(cmd_ctx, "trace buffer %s (%s)",
3483 (xscale->trace.buffer_enabled) ? "enabled" : "disabled",
3484 (xscale->trace.buffer_fill > 0) ? "fill" : "wrap");
3485
3486 dcsr_value = buf_get_u32(xscale->reg_cache->reg_list[XSCALE_DCSR].value, 0, 32);
3487 if (xscale->trace.buffer_fill >= 0)
3488 xscale_write_dcsr_sw(target, (dcsr_value & 0xfffffffc) | 2);
3489 else
3490 xscale_write_dcsr_sw(target, dcsr_value & 0xfffffffc);
3491
3492 return ERROR_OK;
3493 }
3494
3495 int xscale_handle_trace_image_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3496 {
3497 target_t *target;
3498 armv4_5_common_t *armv4_5;
3499 xscale_common_t *xscale;
3500
3501 if (argc < 1)
3502 {
3503 command_print(cmd_ctx, "usage: xscale trace_image <file> [base address] [type]");
3504 return ERROR_OK;
3505 }
3506
3507 target = get_current_target(cmd_ctx);
3508
3509 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3510 {
3511 return ERROR_OK;
3512 }
3513
3514 if (xscale->trace.image)
3515 {
3516 image_close(xscale->trace.image);
3517 free(xscale->trace.image);
3518 command_print(cmd_ctx, "previously loaded image found and closed");
3519 }
3520
3521 xscale->trace.image = malloc(sizeof(image_t));
3522 xscale->trace.image->base_address_set = 0;
3523 xscale->trace.image->start_address_set = 0;
3524
3525 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
3526 if (argc >= 2)
3527 {
3528 xscale->trace.image->base_address_set = 1;
3529 xscale->trace.image->base_address = strtoul(args[1], NULL, 0);
3530 }
3531 else
3532 {
3533 xscale->trace.image->base_address_set = 0;
3534 }
3535
3536 if (image_open(xscale->trace.image, args[0], (argc >= 3) ? args[2] : NULL) != ERROR_OK)
3537 {
3538 free(xscale->trace.image);
3539 xscale->trace.image = NULL;
3540 return ERROR_OK;
3541 }
3542
3543 return ERROR_OK;
3544 }
3545
3546 int xscale_handle_dump_trace_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3547 {
3548 target_t *target = get_current_target(cmd_ctx);
3549 armv4_5_common_t *armv4_5;
3550 xscale_common_t *xscale;
3551 xscale_trace_data_t *trace_data;
3552 fileio_t file;
3553
3554 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3555 {
3556 return ERROR_OK;
3557 }
3558
3559 if (target->state != TARGET_HALTED)
3560 {
3561 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
3562 return ERROR_OK;
3563 }
3564
3565 if (argc < 1)
3566 {
3567 command_print(cmd_ctx, "usage: xscale dump_trace <file>");
3568 return ERROR_OK;
3569 }
3570
3571 trace_data = xscale->trace.data;
3572
3573 if (!trace_data)
3574 {
3575 command_print(cmd_ctx, "no trace data collected");
3576 return ERROR_OK;
3577 }
3578
3579 if (fileio_open(&file, args[0], FILEIO_WRITE, FILEIO_BINARY) != ERROR_OK)
3580 {
3581 return ERROR_OK;
3582 }
3583
3584 while (trace_data)
3585 {
3586 int i;
3587
3588 fileio_write_u32(&file, trace_data->chkpt0);
3589 fileio_write_u32(&file, trace_data->chkpt1);
3590 fileio_write_u32(&file, trace_data->last_instruction);
3591 fileio_write_u32(&file, trace_data->depth);
3592
3593 for (i = 0; i < trace_data->depth; i++)
3594 fileio_write_u32(&file, trace_data->entries[i].data | ((trace_data->entries[i].type & 0xffff) << 16));
3595
3596 trace_data = trace_data->next;
3597 }
3598
3599 fileio_close(&file);
3600
3601 return ERROR_OK;
3602 }
3603
3604 int xscale_handle_analyze_trace_buffer_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
3605 {
3606 target_t *target = get_current_target(cmd_ctx);
3607 armv4_5_common_t *armv4_5;
3608 xscale_common_t *xscale;
3609
3610 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3611 {
3612 return ERROR_OK;
3613 }
3614
3615 xscale_analyze_trace(target, cmd_ctx);
3616
3617 return ERROR_OK;
3618 }
3619
3620 int xscale_handle_cp15(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
3621 {
3622 target_t *target = get_current_target(cmd_ctx);
3623 armv4_5_common_t *armv4_5;
3624 xscale_common_t *xscale;
3625
3626 if (xscale_get_arch_pointers(target, &armv4_5, &xscale) != ERROR_OK)
3627 {
3628 return ERROR_OK;
3629 }
3630
3631 if (target->state != TARGET_HALTED)
3632 {
3633 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
3634 return ERROR_OK;
3635 }
3636 u32 reg_no = 0;
3637 reg_t *reg = NULL;
3638 if(argc > 0)
3639 {
3640 reg_no = strtoul(args[0], NULL, 0);
3641 /*translate from xscale cp15 register no to openocd register*/
3642 switch(reg_no)
3643 {
3644 case 0:
3645 reg_no = XSCALE_MAINID;
3646 break;
3647 case 1:
3648 reg_no = XSCALE_CTRL;
3649 break;
3650 case 2:
3651 reg_no = XSCALE_TTB;
3652 break;
3653 case 3:
3654 reg_no = XSCALE_DAC;
3655 break;
3656 case 5:
3657 reg_no = XSCALE_FSR;
3658 break;
3659 case 6:
3660 reg_no = XSCALE_FAR;
3661 break;
3662 case 13:
3663 reg_no = XSCALE_PID;
3664 break;
3665 case 15:
3666 reg_no = XSCALE_CPACCESS;
3667 break;
3668 default:
3669 command_print(cmd_ctx, "invalid register number");
3670 return ERROR_INVALID_ARGUMENTS;
3671 }
3672 reg = &xscale->reg_cache->reg_list[reg_no];
3673
3674 }
3675 if(argc == 1)
3676 {
3677 u32 value;
3678
3679 /* read cp15 control register */
3680 xscale_get_reg(reg);
3681 value = buf_get_u32(reg->value, 0, 32);
3682 command_print(cmd_ctx, "%s (/%i): 0x%x", reg->name, reg->size, value);
3683 }
3684 else if(argc == 2)
3685 {
3686
3687 u32 value = strtoul(args[1], NULL, 0);
3688
3689 /* send CP write request (command 0x41) */
3690 xscale_send_u32(target, 0x41);
3691
3692 /* send CP register number */
3693 xscale_send_u32(target, reg_no);
3694
3695 /* send CP register value */
3696 xscale_send_u32(target, value);
3697
3698 /* execute cpwait to ensure outstanding operations complete */
3699 xscale_send_u32(target, 0x53);
3700 }
3701 else
3702 {
3703 command_print(cmd_ctx, "usage: cp15 [register]<, [value]>");
3704 }
3705
3706 return ERROR_OK;
3707 }
3708
3709 int xscale_register_commands(struct command_context_s *cmd_ctx)
3710 {
3711 command_t *xscale_cmd;
3712
3713 xscale_cmd = register_command(cmd_ctx, NULL, "xscale", NULL, COMMAND_ANY, "xscale specific commands");
3714
3715 register_command(cmd_ctx, xscale_cmd, "debug_handler", xscale_handle_debug_handler_command, COMMAND_ANY, "'xscale debug_handler <target#> <address>' command takes two required operands");
3716 register_command(cmd_ctx, xscale_cmd, "cache_clean_address", xscale_handle_cache_clean_address_command, COMMAND_ANY, NULL);
3717
3718 register_command(cmd_ctx, xscale_cmd, "cache_info", xscale_handle_cache_info_command, COMMAND_EXEC, NULL);
3719 register_command(cmd_ctx, xscale_cmd, "mmu", xscale_handle_mmu_command, COMMAND_EXEC, "['enable'|'disable'] the MMU");
3720 register_command(cmd_ctx, xscale_cmd, "icache", xscale_handle_idcache_command, COMMAND_EXEC, "['enable'|'disable'] the ICache");
3721 register_command(cmd_ctx, xscale_cmd, "dcache", xscale_handle_idcache_command, COMMAND_EXEC, "['enable'|'disable'] the DCache");
3722
3723 register_command(cmd_ctx, xscale_cmd, "vector_catch", xscale_handle_idcache_command, COMMAND_EXEC, "<mask> of vectors that should be catched");
3724
3725 register_command(cmd_ctx, xscale_cmd, "trace_buffer", xscale_handle_trace_buffer_command, COMMAND_EXEC, "<enable|disable> ['fill' [n]|'wrap']");
3726
3727 register_command(cmd_ctx, xscale_cmd, "dump_trace", xscale_handle_dump_trace_command, COMMAND_EXEC, "dump content of trace buffer to <file>");
3728 register_command(cmd_ctx, xscale_cmd, "analyze_trace", xscale_handle_analyze_trace_buffer_command, COMMAND_EXEC, "analyze content of trace buffer");
3729 register_command(cmd_ctx, xscale_cmd, "trace_image", xscale_handle_trace_image_command,
3730 COMMAND_EXEC, "load image from <file> [base address]");
3731
3732 register_command(cmd_ctx, xscale_cmd, "cp15", xscale_handle_cp15, COMMAND_EXEC, "access coproc 15 <register> [value]");
3733
3734 armv4_5_register_commands(cmd_ctx);
3735
3736 return ERROR_OK;
3737 }

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)