1 /***************************************************************************
2 * Copyright (C) 2006, 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * Copyright (C) 2007,2008 Øyvind Harboe *
6 * oyvind.harboe@zylin.com *
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. *
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. *
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 ***************************************************************************/
28 #include "target_type.h"
29 #include "arm7_9_common.h"
30 #include "arm_simulator.h"
31 #include "arm_disassembler.h"
32 #include "time_support.h"
36 int xscale_register_commands(struct command_context_s
*cmd_ctx
);
38 /* forward declarations */
39 int xscale_target_create(struct target_s
*target
, Jim_Interp
*interp
);
40 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
41 int xscale_quit(void);
43 int xscale_arch_state(struct target_s
*target
);
44 int xscale_poll(target_t
*target
);
45 int xscale_halt(target_t
*target
);
46 int xscale_resume(struct target_s
*target
, int current
, uint32_t address
, int handle_breakpoints
, int debug_execution
);
47 int xscale_step(struct target_s
*target
, int current
, uint32_t address
, int handle_breakpoints
);
48 int xscale_debug_entry(target_t
*target
);
49 int xscale_restore_context(target_t
*target
);
51 int xscale_assert_reset(target_t
*target
);
52 int xscale_deassert_reset(target_t
*target
);
53 int xscale_soft_reset_halt(struct target_s
*target
);
55 int xscale_set_reg_u32(reg_t
*reg
, uint32_t value
);
57 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
);
58 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, uint32_t value
);
60 int xscale_read_memory(struct target_s
*target
, uint32_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
);
61 int xscale_write_memory(struct target_s
*target
, uint32_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
);
62 int xscale_bulk_write_memory(target_t
*target
, uint32_t address
, uint32_t count
, uint8_t *buffer
);
64 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
65 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
66 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
67 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
68 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
69 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
70 void xscale_enable_watchpoints(struct target_s
*target
);
71 void xscale_enable_breakpoints(struct target_s
*target
);
72 static int xscale_virt2phys(struct target_s
*target
, uint32_t virtual, uint32_t *physical
);
73 static int xscale_mmu(struct target_s
*target
, int *enabled
);
75 int xscale_read_trace(target_t
*target
);
77 target_type_t xscale_target
=
82 .arch_state
= xscale_arch_state
,
84 .target_request_data
= NULL
,
87 .resume
= xscale_resume
,
90 .assert_reset
= xscale_assert_reset
,
91 .deassert_reset
= xscale_deassert_reset
,
92 .soft_reset_halt
= xscale_soft_reset_halt
,
94 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
96 .read_memory
= xscale_read_memory
,
97 .write_memory
= xscale_write_memory
,
98 .bulk_write_memory
= xscale_bulk_write_memory
,
99 .checksum_memory
= arm7_9_checksum_memory
,
100 .blank_check_memory
= arm7_9_blank_check_memory
,
102 .run_algorithm
= armv4_5_run_algorithm
,
104 .add_breakpoint
= xscale_add_breakpoint
,
105 .remove_breakpoint
= xscale_remove_breakpoint
,
106 .add_watchpoint
= xscale_add_watchpoint
,
107 .remove_watchpoint
= xscale_remove_watchpoint
,
109 .register_commands
= xscale_register_commands
,
110 .target_create
= xscale_target_create
,
111 .init_target
= xscale_init_target
,
114 .virt2phys
= xscale_virt2phys
,
118 char* xscale_reg_list
[] =
120 "XSCALE_MAINID", /* 0 */
130 "XSCALE_IBCR0", /* 10 */
140 "XSCALE_RX", /* 20 */
144 xscale_reg_t xscale_reg_arch_info
[] =
146 {XSCALE_MAINID
, NULL
},
147 {XSCALE_CACHETYPE
, NULL
},
149 {XSCALE_AUXCTRL
, NULL
},
155 {XSCALE_CPACCESS
, NULL
},
156 {XSCALE_IBCR0
, NULL
},
157 {XSCALE_IBCR1
, NULL
},
160 {XSCALE_DBCON
, NULL
},
161 {XSCALE_TBREG
, NULL
},
162 {XSCALE_CHKPT0
, NULL
},
163 {XSCALE_CHKPT1
, NULL
},
164 {XSCALE_DCSR
, NULL
}, /* DCSR accessed via JTAG or SW */
165 {-1, NULL
}, /* TX accessed via JTAG */
166 {-1, NULL
}, /* RX accessed via JTAG */
167 {-1, NULL
}, /* TXRXCTRL implicit access via JTAG */
170 int xscale_reg_arch_type
= -1;
172 int xscale_get_reg(reg_t
*reg
);
173 int xscale_set_reg(reg_t
*reg
, uint8_t *buf
);
175 int xscale_get_arch_pointers(target_t
*target
, armv4_5_common_t
**armv4_5_p
, xscale_common_t
**xscale_p
)
177 armv4_5_common_t
*armv4_5
= target
->arch_info
;
178 xscale_common_t
*xscale
= armv4_5
->arch_info
;
180 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
182 LOG_ERROR("target isn't an XScale target");
186 if (xscale
->common_magic
!= XSCALE_COMMON_MAGIC
)
188 LOG_ERROR("target isn't an XScale target");
192 *armv4_5_p
= armv4_5
;
198 int xscale_jtag_set_instr(jtag_tap_t
*tap
, uint32_t new_instr
)
203 if (buf_get_u32(tap
->cur_instr
, 0, tap
->ir_length
) != new_instr
)
208 field
.num_bits
= tap
->ir_length
;
209 field
.out_value
= calloc(CEIL(field
.num_bits
, 8), 1);
210 buf_set_u32(field
.out_value
, 0, field
.num_bits
, new_instr
);
213 field
.in_value
= tmp
;
215 jtag_add_ir_scan(1, &field
, jtag_get_end_state());
217 /* FIX!!!! isn't this check superfluous? verify_ircapture handles this? */
218 jtag_check_value_mask(&field
, tap
->expected
, tap
->expected_mask
);
220 free(field
.out_value
);
226 int xscale_read_dcsr(target_t
*target
)
228 armv4_5_common_t
*armv4_5
= target
->arch_info
;
229 xscale_common_t
*xscale
= armv4_5
->arch_info
;
233 scan_field_t fields
[3];
234 uint8_t field0
= 0x0;
235 uint8_t field0_check_value
= 0x2;
236 uint8_t field0_check_mask
= 0x7;
237 uint8_t field2
= 0x0;
238 uint8_t field2_check_value
= 0x0;
239 uint8_t field2_check_mask
= 0x1;
241 jtag_set_end_state(TAP_DRPAUSE
);
242 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
244 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
245 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
247 fields
[0].tap
= xscale
->jtag_info
.tap
;
248 fields
[0].num_bits
= 3;
249 fields
[0].out_value
= &field0
;
251 fields
[0].in_value
= &tmp
;
253 fields
[1].tap
= xscale
->jtag_info
.tap
;
254 fields
[1].num_bits
= 32;
255 fields
[1].out_value
= NULL
;
256 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
259 fields
[2].tap
= xscale
->jtag_info
.tap
;
260 fields
[2].num_bits
= 1;
261 fields
[2].out_value
= &field2
;
263 fields
[2].in_value
= &tmp2
;
265 jtag_add_dr_scan(3, fields
, jtag_get_end_state());
267 jtag_check_value_mask(fields
+0, &field0_check_value
, &field0_check_mask
);
268 jtag_check_value_mask(fields
+2, &field2_check_value
, &field2_check_mask
);
270 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
272 LOG_ERROR("JTAG error while reading DCSR");
276 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
277 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
279 /* write the register with the value we just read
280 * on this second pass, only the first bit of field0 is guaranteed to be 0)
282 field0_check_mask
= 0x1;
283 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
284 fields
[1].in_value
= NULL
;
286 jtag_set_end_state(TAP_IDLE
);
288 jtag_add_dr_scan(3, fields
, jtag_get_end_state());
290 /* DANGER!!! this must be here. It will make sure that the arguments
291 * to jtag_set_check_value() does not go out of scope! */
292 return jtag_execute_queue();
296 static void xscale_getbuf(jtag_callback_data_t arg
)
298 uint8_t *in
=(uint8_t *)arg
;
299 *((uint32_t *)in
)=buf_get_u32(in
, 0, 32);
302 int xscale_receive(target_t
*target
, uint32_t *buffer
, int num_words
)
305 return ERROR_INVALID_ARGUMENTS
;
308 armv4_5_common_t
*armv4_5
= target
->arch_info
;
309 xscale_common_t
*xscale
= armv4_5
->arch_info
;
312 scan_field_t fields
[3];
314 uint8_t *field0
= malloc(num_words
* 1);
315 uint8_t field0_check_value
= 0x2;
316 uint8_t field0_check_mask
= 0x6;
317 uint32_t *field1
= malloc(num_words
* 4);
318 uint8_t field2_check_value
= 0x0;
319 uint8_t field2_check_mask
= 0x1;
321 int words_scheduled
= 0;
325 path
[0] = TAP_DRSELECT
;
326 path
[1] = TAP_DRCAPTURE
;
327 path
[2] = TAP_DRSHIFT
;
329 fields
[0].tap
= xscale
->jtag_info
.tap
;
330 fields
[0].num_bits
= 3;
331 fields
[0].out_value
= NULL
;
332 fields
[0].in_value
= NULL
;
333 fields
[0].check_value
= &field0_check_value
;
334 fields
[0].check_mask
= &field0_check_mask
;
336 fields
[1].tap
= xscale
->jtag_info
.tap
;
337 fields
[1].num_bits
= 32;
338 fields
[1].out_value
= NULL
;
339 fields
[1].check_value
= NULL
;
340 fields
[1].check_mask
= NULL
;
342 fields
[2].tap
= xscale
->jtag_info
.tap
;
343 fields
[2].num_bits
= 1;
344 fields
[2].out_value
= NULL
;
345 fields
[2].in_value
= NULL
;
346 fields
[2].check_value
= &field2_check_value
;
347 fields
[2].check_mask
= &field2_check_mask
;
349 jtag_set_end_state(TAP_IDLE
);
350 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgtx
);
351 jtag_add_runtest(1, jtag_get_end_state()); /* ensures that we're in the TAP_IDLE state as the above could be a no-op */
353 /* repeat until all words have been collected */
355 while (words_done
< num_words
)
359 for (i
= words_done
; i
< num_words
; i
++)
361 fields
[0].in_value
= &field0
[i
];
363 jtag_add_pathmove(3, path
);
365 fields
[1].in_value
= (uint8_t *)(field1
+i
);
367 jtag_add_dr_scan_check(3, fields
, jtag_set_end_state(TAP_IDLE
));
369 jtag_add_callback(xscale_getbuf
, (jtag_callback_data_t
)(field1
+i
));
374 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
376 LOG_ERROR("JTAG error while receiving data from debug handler");
380 /* examine results */
381 for (i
= words_done
; i
< num_words
; i
++)
383 if (!(field0
[0] & 1))
385 /* move backwards if necessary */
387 for (j
= i
; j
< num_words
- 1; j
++)
389 field0
[j
] = field0
[j
+1];
390 field1
[j
] = field1
[j
+1];
395 if (words_scheduled
==0)
397 if (attempts
++==1000)
399 LOG_ERROR("Failed to receiving data from debug handler after 1000 attempts");
400 retval
=ERROR_TARGET_TIMEOUT
;
405 words_done
+= words_scheduled
;
408 for (i
= 0; i
< num_words
; i
++)
409 *(buffer
++) = buf_get_u32((uint8_t*)&field1
[i
], 0, 32);
416 int xscale_read_tx(target_t
*target
, int consume
)
418 armv4_5_common_t
*armv4_5
= target
->arch_info
;
419 xscale_common_t
*xscale
= armv4_5
->arch_info
;
421 tap_state_t noconsume_path
[6];
424 struct timeval timeout
, now
;
426 scan_field_t fields
[3];
427 uint8_t field0_in
= 0x0;
428 uint8_t field0_check_value
= 0x2;
429 uint8_t field0_check_mask
= 0x6;
430 uint8_t field2_check_value
= 0x0;
431 uint8_t field2_check_mask
= 0x1;
433 jtag_set_end_state(TAP_IDLE
);
435 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgtx
);
437 path
[0] = TAP_DRSELECT
;
438 path
[1] = TAP_DRCAPTURE
;
439 path
[2] = TAP_DRSHIFT
;
441 noconsume_path
[0] = TAP_DRSELECT
;
442 noconsume_path
[1] = TAP_DRCAPTURE
;
443 noconsume_path
[2] = TAP_DREXIT1
;
444 noconsume_path
[3] = TAP_DRPAUSE
;
445 noconsume_path
[4] = TAP_DREXIT2
;
446 noconsume_path
[5] = TAP_DRSHIFT
;
448 fields
[0].tap
= xscale
->jtag_info
.tap
;
449 fields
[0].num_bits
= 3;
450 fields
[0].out_value
= NULL
;
451 fields
[0].in_value
= &field0_in
;
453 fields
[1].tap
= xscale
->jtag_info
.tap
;
454 fields
[1].num_bits
= 32;
455 fields
[1].out_value
= NULL
;
456 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
;
459 fields
[2].tap
= xscale
->jtag_info
.tap
;
460 fields
[2].num_bits
= 1;
461 fields
[2].out_value
= NULL
;
463 fields
[2].in_value
= &tmp
;
465 gettimeofday(&timeout
, NULL
);
466 timeval_add_time(&timeout
, 1, 0);
470 /* if we want to consume the register content (i.e. clear TX_READY),
471 * we have to go straight from Capture-DR to Shift-DR
472 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
475 jtag_add_pathmove(3, path
);
478 jtag_add_pathmove(sizeof(noconsume_path
)/sizeof(*noconsume_path
), noconsume_path
);
481 jtag_add_dr_scan(3, fields
, jtag_set_end_state(TAP_IDLE
));
483 jtag_check_value_mask(fields
+0, &field0_check_value
, &field0_check_mask
);
484 jtag_check_value_mask(fields
+2, &field2_check_value
, &field2_check_mask
);
486 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
488 LOG_ERROR("JTAG error while reading TX");
489 return ERROR_TARGET_TIMEOUT
;
492 gettimeofday(&now
, NULL
);
493 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
495 LOG_ERROR("time out reading TX register");
496 return ERROR_TARGET_TIMEOUT
;
498 if (!((!(field0_in
& 1)) && consume
))
504 LOG_DEBUG("waiting 100ms");
505 alive_sleep(100); /* avoid flooding the logs */
513 if (!(field0_in
& 1))
514 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
519 int xscale_write_rx(target_t
*target
)
521 armv4_5_common_t
*armv4_5
= target
->arch_info
;
522 xscale_common_t
*xscale
= armv4_5
->arch_info
;
525 struct timeval timeout
, now
;
527 scan_field_t fields
[3];
528 uint8_t field0_out
= 0x0;
529 uint8_t field0_in
= 0x0;
530 uint8_t field0_check_value
= 0x2;
531 uint8_t field0_check_mask
= 0x6;
532 uint8_t field2
= 0x0;
533 uint8_t field2_check_value
= 0x0;
534 uint8_t field2_check_mask
= 0x1;
536 jtag_set_end_state(TAP_IDLE
);
538 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgrx
);
540 fields
[0].tap
= xscale
->jtag_info
.tap
;
541 fields
[0].num_bits
= 3;
542 fields
[0].out_value
= &field0_out
;
543 fields
[0].in_value
= &field0_in
;
545 fields
[1].tap
= xscale
->jtag_info
.tap
;
546 fields
[1].num_bits
= 32;
547 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
;
548 fields
[1].in_value
= NULL
;
551 fields
[2].tap
= xscale
->jtag_info
.tap
;
552 fields
[2].num_bits
= 1;
553 fields
[2].out_value
= &field2
;
555 fields
[2].in_value
= &tmp
;
557 gettimeofday(&timeout
, NULL
);
558 timeval_add_time(&timeout
, 1, 0);
560 /* poll until rx_read is low */
561 LOG_DEBUG("polling RX");
564 jtag_add_dr_scan(3, fields
, jtag_set_end_state(TAP_IDLE
));
566 jtag_check_value_mask(fields
+0, &field0_check_value
, &field0_check_mask
);
567 jtag_check_value_mask(fields
+2, &field2_check_value
, &field2_check_mask
);
569 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
571 LOG_ERROR("JTAG error while writing RX");
575 gettimeofday(&now
, NULL
);
576 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
578 LOG_ERROR("time out writing RX register");
579 return ERROR_TARGET_TIMEOUT
;
581 if (!(field0_in
& 1))
585 LOG_DEBUG("waiting 100ms");
586 alive_sleep(100); /* avoid flooding the logs */
596 jtag_add_dr_scan(3, fields
, jtag_set_end_state(TAP_IDLE
));
598 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
600 LOG_ERROR("JTAG error while writing RX");
607 /* send count elements of size byte to the debug handler */
608 int xscale_send(target_t
*target
, uint8_t *buffer
, int count
, int size
)
610 armv4_5_common_t
*armv4_5
= target
->arch_info
;
611 xscale_common_t
*xscale
= armv4_5
->arch_info
;
619 jtag_set_end_state(TAP_IDLE
);
621 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgrx
);
628 int endianness
= target
->endianness
;
629 while (done_count
++ < count
)
634 if (endianness
== TARGET_LITTLE_ENDIAN
)
636 t
[1]=le_to_h_u32(buffer
);
639 t
[1]=be_to_h_u32(buffer
);
643 if (endianness
== TARGET_LITTLE_ENDIAN
)
645 t
[1]=le_to_h_u16(buffer
);
648 t
[1]=be_to_h_u16(buffer
);
655 LOG_ERROR("BUG: size neither 4, 2 nor 1");
658 jtag_add_dr_out(xscale
->jtag_info
.tap
,
662 jtag_set_end_state(TAP_IDLE
));
666 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
668 LOG_ERROR("JTAG error while sending data to debug handler");
675 int xscale_send_u32(target_t
*target
, uint32_t value
)
677 armv4_5_common_t
*armv4_5
= target
->arch_info
;
678 xscale_common_t
*xscale
= armv4_5
->arch_info
;
680 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
681 return xscale_write_rx(target
);
684 int xscale_write_dcsr(target_t
*target
, int hold_rst
, int ext_dbg_brk
)
686 armv4_5_common_t
*armv4_5
= target
->arch_info
;
687 xscale_common_t
*xscale
= armv4_5
->arch_info
;
691 scan_field_t fields
[3];
692 uint8_t field0
= 0x0;
693 uint8_t field0_check_value
= 0x2;
694 uint8_t field0_check_mask
= 0x7;
695 uint8_t field2
= 0x0;
696 uint8_t field2_check_value
= 0x0;
697 uint8_t field2_check_mask
= 0x1;
700 xscale
->hold_rst
= hold_rst
;
702 if (ext_dbg_brk
!= -1)
703 xscale
->external_debug_break
= ext_dbg_brk
;
705 jtag_set_end_state(TAP_IDLE
);
706 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
708 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
709 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
711 fields
[0].tap
= xscale
->jtag_info
.tap
;
712 fields
[0].num_bits
= 3;
713 fields
[0].out_value
= &field0
;
715 fields
[0].in_value
= &tmp
;
717 fields
[1].tap
= xscale
->jtag_info
.tap
;
718 fields
[1].num_bits
= 32;
719 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
720 fields
[1].in_value
= NULL
;
723 fields
[2].tap
= xscale
->jtag_info
.tap
;
724 fields
[2].num_bits
= 1;
725 fields
[2].out_value
= &field2
;
727 fields
[2].in_value
= &tmp2
;
729 jtag_add_dr_scan(3, fields
, jtag_get_end_state());
731 jtag_check_value_mask(fields
+0, &field0_check_value
, &field0_check_mask
);
732 jtag_check_value_mask(fields
+2, &field2_check_value
, &field2_check_mask
);
734 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
736 LOG_ERROR("JTAG error while writing DCSR");
740 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
741 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
746 /* parity of the number of bits 0 if even; 1 if odd. for 32 bit words */
747 unsigned int parity (unsigned int v
)
754 LOG_DEBUG("parity of 0x%x is %i", ov
, (0x6996 >> v
) & 1);
755 return (0x6996 >> v
) & 1;
758 int xscale_load_ic(target_t
*target
, int mini
, uint32_t va
, uint32_t buffer
[8])
760 armv4_5_common_t
*armv4_5
= target
->arch_info
;
761 xscale_common_t
*xscale
= armv4_5
->arch_info
;
766 scan_field_t fields
[2];
768 LOG_DEBUG("loading miniIC at 0x%8.8" PRIx32
"", va
);
770 jtag_set_end_state(TAP_IDLE
);
771 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.ldic
); /* LDIC */
773 /* CMD is b010 for Main IC and b011 for Mini IC */
775 buf_set_u32(&cmd
, 0, 3, 0x3);
777 buf_set_u32(&cmd
, 0, 3, 0x2);
779 buf_set_u32(&cmd
, 3, 3, 0x0);
781 /* virtual address of desired cache line */
782 buf_set_u32(packet
, 0, 27, va
>> 5);
784 fields
[0].tap
= xscale
->jtag_info
.tap
;
785 fields
[0].num_bits
= 6;
786 fields
[0].out_value
= &cmd
;
788 fields
[0].in_value
= NULL
;
794 fields
[1].tap
= xscale
->jtag_info
.tap
;
795 fields
[1].num_bits
= 27;
796 fields
[1].out_value
= packet
;
798 fields
[1].in_value
= NULL
;
804 jtag_add_dr_scan(2, fields
, jtag_get_end_state());
806 fields
[0].num_bits
= 32;
807 fields
[0].out_value
= packet
;
809 fields
[1].num_bits
= 1;
810 fields
[1].out_value
= &cmd
;
812 for (word
= 0; word
< 8; word
++)
814 buf_set_u32(packet
, 0, 32, buffer
[word
]);
817 memcpy(&value
, packet
, sizeof(uint32_t));
820 jtag_add_dr_scan(2, fields
, jtag_get_end_state());
823 jtag_execute_queue();
828 int xscale_invalidate_ic_line(target_t
*target
, uint32_t va
)
830 armv4_5_common_t
*armv4_5
= target
->arch_info
;
831 xscale_common_t
*xscale
= armv4_5
->arch_info
;
835 scan_field_t fields
[2];
837 jtag_set_end_state(TAP_IDLE
);
838 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.ldic
); /* LDIC */
840 /* CMD for invalidate IC line b000, bits [6:4] b000 */
841 buf_set_u32(&cmd
, 0, 6, 0x0);
843 /* virtual address of desired cache line */
844 buf_set_u32(packet
, 0, 27, va
>> 5);
846 fields
[0].tap
= xscale
->jtag_info
.tap
;
847 fields
[0].num_bits
= 6;
848 fields
[0].out_value
= &cmd
;
850 fields
[0].in_value
= NULL
;
856 fields
[1].tap
= xscale
->jtag_info
.tap
;
857 fields
[1].num_bits
= 27;
858 fields
[1].out_value
= packet
;
860 fields
[1].in_value
= NULL
;
866 jtag_add_dr_scan(2, fields
, jtag_get_end_state());
871 int xscale_update_vectors(target_t
*target
)
873 armv4_5_common_t
*armv4_5
= target
->arch_info
;
874 xscale_common_t
*xscale
= armv4_5
->arch_info
;
878 uint32_t low_reset_branch
, high_reset_branch
;
880 for (i
= 1; i
< 8; i
++)
882 /* if there's a static vector specified for this exception, override */
883 if (xscale
->static_high_vectors_set
& (1 << i
))
885 xscale
->high_vectors
[i
] = xscale
->static_high_vectors
[i
];
889 retval
=target_read_u32(target
, 0xffff0000 + 4*i
, &xscale
->high_vectors
[i
]);
890 if (retval
== ERROR_TARGET_TIMEOUT
)
892 if (retval
!= ERROR_OK
)
894 /* Some of these reads will fail as part of normal execution */
895 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
900 for (i
= 1; i
< 8; i
++)
902 if (xscale
->static_low_vectors_set
& (1 << i
))
904 xscale
->low_vectors
[i
] = xscale
->static_low_vectors
[i
];
908 retval
=target_read_u32(target
, 0x0 + 4*i
, &xscale
->low_vectors
[i
]);
909 if (retval
== ERROR_TARGET_TIMEOUT
)
911 if (retval
!= ERROR_OK
)
913 /* Some of these reads will fail as part of normal execution */
914 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
919 /* calculate branches to debug handler */
920 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
921 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
923 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
924 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
926 /* invalidate and load exception vectors in mini i-cache */
927 xscale_invalidate_ic_line(target
, 0x0);
928 xscale_invalidate_ic_line(target
, 0xffff0000);
930 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
931 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
936 int xscale_arch_state(struct target_s
*target
)
938 armv4_5_common_t
*armv4_5
= target
->arch_info
;
939 xscale_common_t
*xscale
= armv4_5
->arch_info
;
943 "disabled", "enabled"
946 char *arch_dbg_reason
[] =
948 "", "\n(processor reset)", "\n(trace buffer full)"
951 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
953 LOG_ERROR("BUG: called for a non-ARMv4/5 target");
957 LOG_USER("target halted in %s state due to %s, current mode: %s\n"
958 "cpsr: 0x%8.8" PRIx32
" pc: 0x%8.8" PRIx32
"\n"
959 "MMU: %s, D-Cache: %s, I-Cache: %s"
961 armv4_5_state_strings
[armv4_5
->core_state
],
962 Jim_Nvp_value2name_simple( nvp_target_debug_reason
, target
->debug_reason
)->name
,
963 armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)],
964 buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32),
965 buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32),
966 state
[xscale
->armv4_5_mmu
.mmu_enabled
],
967 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
],
968 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
],
969 arch_dbg_reason
[xscale
->arch_debug_reason
]);
974 int xscale_poll(target_t
*target
)
977 armv4_5_common_t
*armv4_5
= target
->arch_info
;
978 xscale_common_t
*xscale
= armv4_5
->arch_info
;
980 if ((target
->state
== TARGET_RUNNING
) || (target
->state
== TARGET_DEBUG_RUNNING
))
982 enum target_state previous_state
= target
->state
;
983 if ((retval
= xscale_read_tx(target
, 0)) == ERROR_OK
)
986 /* there's data to read from the tx register, we entered debug state */
987 xscale
->handler_running
= 1;
989 target
->state
= TARGET_HALTED
;
991 /* process debug entry, fetching current mode regs */
992 retval
= xscale_debug_entry(target
);
994 else if (retval
!= ERROR_TARGET_RESOURCE_NOT_AVAILABLE
)
996 LOG_USER("error while polling TX register, reset CPU");
997 /* here we "lie" so GDB won't get stuck and a reset can be perfomed */
998 target
->state
= TARGET_HALTED
;
1001 /* debug_entry could have overwritten target state (i.e. immediate resume)
1002 * don't signal event handlers in that case
1004 if (target
->state
!= TARGET_HALTED
)
1007 /* if target was running, signal that we halted
1008 * otherwise we reentered from debug execution */
1009 if (previous_state
== TARGET_RUNNING
)
1010 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1012 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_HALTED
);
1018 int xscale_debug_entry(target_t
*target
)
1020 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1021 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1023 uint32_t buffer
[10];
1029 /* clear external dbg break (will be written on next DCSR read) */
1030 xscale
->external_debug_break
= 0;
1031 if ((retval
=xscale_read_dcsr(target
)) != ERROR_OK
)
1034 /* get r0, pc, r1 to r7 and cpsr */
1035 if ((retval
=xscale_receive(target
, buffer
, 10)) != ERROR_OK
)
1038 /* move r0 from buffer to register cache */
1039 buf_set_u32(armv4_5
->core_cache
->reg_list
[0].value
, 0, 32, buffer
[0]);
1040 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1041 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1042 LOG_DEBUG("r0: 0x%8.8" PRIx32
"", buffer
[0]);
1044 /* move pc from buffer to register cache */
1045 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, buffer
[1]);
1046 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1047 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1048 LOG_DEBUG("pc: 0x%8.8" PRIx32
"", buffer
[1]);
1050 /* move data from buffer to register cache */
1051 for (i
= 1; i
<= 7; i
++)
1053 buf_set_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32, buffer
[1 + i
]);
1054 armv4_5
->core_cache
->reg_list
[i
].dirty
= 1;
1055 armv4_5
->core_cache
->reg_list
[i
].valid
= 1;
1056 LOG_DEBUG("r%i: 0x%8.8" PRIx32
"", i
, buffer
[i
+ 1]);
1059 buf_set_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32, buffer
[9]);
1060 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].dirty
= 1;
1061 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].valid
= 1;
1062 LOG_DEBUG("cpsr: 0x%8.8" PRIx32
"", buffer
[9]);
1064 armv4_5
->core_mode
= buffer
[9] & 0x1f;
1065 if (armv4_5_mode_to_number(armv4_5
->core_mode
) == -1)
1067 target
->state
= TARGET_UNKNOWN
;
1068 LOG_ERROR("cpsr contains invalid mode value - communication failure");
1069 return ERROR_TARGET_FAILURE
;
1071 LOG_DEBUG("target entered debug state in %s mode", armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)]);
1073 if (buffer
[9] & 0x20)
1074 armv4_5
->core_state
= ARMV4_5_STATE_THUMB
;
1076 armv4_5
->core_state
= ARMV4_5_STATE_ARM
;
1079 if (armv4_5_mode_to_number(armv4_5
->core_mode
)==-1)
1082 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1083 if ((armv4_5
->core_mode
!= ARMV4_5_MODE_USR
) && (armv4_5
->core_mode
!= ARMV4_5_MODE_SYS
))
1085 xscale_receive(target
, buffer
, 8);
1086 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1087 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).dirty
= 0;
1088 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).valid
= 1;
1092 /* r8 to r14, but no spsr */
1093 xscale_receive(target
, buffer
, 7);
1096 /* move data from buffer to register cache */
1097 for (i
= 8; i
<= 14; i
++)
1099 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).value
, 0, 32, buffer
[i
- 8]);
1100 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).dirty
= 0;
1101 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).valid
= 1;
1104 /* examine debug reason */
1105 xscale_read_dcsr(target
);
1106 moe
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 2, 3);
1108 /* stored PC (for calculating fixup) */
1109 pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1113 case 0x0: /* Processor reset */
1114 target
->debug_reason
= DBG_REASON_DBGRQ
;
1115 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_RESET
;
1118 case 0x1: /* Instruction breakpoint hit */
1119 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1120 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1123 case 0x2: /* Data breakpoint hit */
1124 target
->debug_reason
= DBG_REASON_WATCHPOINT
;
1125 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1128 case 0x3: /* BKPT instruction executed */
1129 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1130 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1133 case 0x4: /* Ext. debug event */
1134 target
->debug_reason
= DBG_REASON_DBGRQ
;
1135 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1138 case 0x5: /* Vector trap occured */
1139 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1140 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1143 case 0x6: /* Trace buffer full break */
1144 target
->debug_reason
= DBG_REASON_DBGRQ
;
1145 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_TB_FULL
;
1148 case 0x7: /* Reserved */
1150 LOG_ERROR("Method of Entry is 'Reserved'");
1155 /* apply PC fixup */
1156 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, pc
);
1158 /* on the first debug entry, identify cache type */
1159 if (xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
== -1)
1161 uint32_t cache_type_reg
;
1163 /* read cp15 cache type register */
1164 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
]);
1165 cache_type_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
].value
, 0, 32);
1167 armv4_5_identify_cache(cache_type_reg
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
1170 /* examine MMU and Cache settings */
1171 /* read cp15 control register */
1172 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
1173 xscale
->cp15_control_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
1174 xscale
->armv4_5_mmu
.mmu_enabled
= (xscale
->cp15_control_reg
& 0x1U
) ? 1 : 0;
1175 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= (xscale
->cp15_control_reg
& 0x4U
) ? 1 : 0;
1176 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= (xscale
->cp15_control_reg
& 0x1000U
) ? 1 : 0;
1178 /* tracing enabled, read collected trace data */
1179 if (xscale
->trace
.buffer_enabled
)
1181 xscale_read_trace(target
);
1182 xscale
->trace
.buffer_fill
--;
1184 /* resume if we're still collecting trace data */
1185 if ((xscale
->arch_debug_reason
== XSCALE_DBG_REASON_TB_FULL
)
1186 && (xscale
->trace
.buffer_fill
> 0))
1188 xscale_resume(target
, 1, 0x0, 1, 0);
1192 xscale
->trace
.buffer_enabled
= 0;
1199 int xscale_halt(target_t
*target
)
1201 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1202 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1204 LOG_DEBUG("target->state: %s",
1205 Jim_Nvp_value2name_simple( nvp_target_state
, target
->state
)->name
);
1207 if (target
->state
== TARGET_HALTED
)
1209 LOG_DEBUG("target was already halted");
1212 else if (target
->state
== TARGET_UNKNOWN
)
1214 /* this must not happen for a xscale target */
1215 LOG_ERROR("target was in unknown state when halt was requested");
1216 return ERROR_TARGET_INVALID
;
1218 else if (target
->state
== TARGET_RESET
)
1220 LOG_DEBUG("target->state == TARGET_RESET");
1224 /* assert external dbg break */
1225 xscale
->external_debug_break
= 1;
1226 xscale_read_dcsr(target
);
1228 target
->debug_reason
= DBG_REASON_DBGRQ
;
1234 int xscale_enable_single_step(struct target_s
*target
, uint32_t next_pc
)
1236 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1237 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1238 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1241 if (xscale
->ibcr0_used
)
1243 breakpoint_t
*ibcr0_bp
= breakpoint_find(target
, buf_get_u32(ibcr0
->value
, 0, 32) & 0xfffffffe);
1247 xscale_unset_breakpoint(target
, ibcr0_bp
);
1251 LOG_ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1256 if ((retval
=xscale_set_reg_u32(ibcr0
, next_pc
| 0x1)) != ERROR_OK
)
1262 int xscale_disable_single_step(struct target_s
*target
)
1264 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1265 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1266 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1269 if ((retval
=xscale_set_reg_u32(ibcr0
, 0x0)) != ERROR_OK
)
1275 int xscale_resume(struct target_s
*target
, int current
, uint32_t address
, int handle_breakpoints
, int debug_execution
)
1277 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1278 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1279 breakpoint_t
*breakpoint
= target
->breakpoints
;
1281 uint32_t current_pc
;
1288 if (target
->state
!= TARGET_HALTED
)
1290 LOG_WARNING("target not halted");
1291 return ERROR_TARGET_NOT_HALTED
;
1294 if (!debug_execution
)
1296 target_free_all_working_areas(target
);
1299 /* update vector tables */
1300 if ((retval
=xscale_update_vectors(target
)) != ERROR_OK
)
1303 /* current = 1: continue on current pc, otherwise continue at <address> */
1305 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1307 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1309 /* if we're at the reset vector, we have to simulate the branch */
1310 if (current_pc
== 0x0)
1312 arm_simulate_step(target
, NULL
);
1313 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1316 /* the front-end may request us not to handle breakpoints */
1317 if (handle_breakpoints
)
1319 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1323 /* there's a breakpoint at the current PC, we have to step over it */
1324 LOG_DEBUG("unset breakpoint at 0x%8.8" PRIx32
"", breakpoint
->address
);
1325 xscale_unset_breakpoint(target
, breakpoint
);
1327 /* calculate PC of next instruction */
1328 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1330 uint32_t current_opcode
;
1331 target_read_u32(target
, current_pc
, ¤t_opcode
);
1332 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8" PRIx32
"", current_opcode
);
1335 LOG_DEBUG("enable single-step");
1336 xscale_enable_single_step(target
, next_pc
);
1338 /* restore banked registers */
1339 xscale_restore_context(target
);
1341 /* send resume request (command 0x30 or 0x31)
1342 * clean the trace buffer if it is to be enabled (0x62) */
1343 if (xscale
->trace
.buffer_enabled
)
1345 xscale_send_u32(target
, 0x62);
1346 xscale_send_u32(target
, 0x31);
1349 xscale_send_u32(target
, 0x30);
1352 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1353 LOG_DEBUG("writing cpsr with value 0x%8.8" PRIx32
"", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1355 for (i
= 7; i
>= 0; i
--)
1358 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1359 LOG_DEBUG("writing r%i with value 0x%8.8" PRIx32
"", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1363 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1364 LOG_DEBUG("writing PC with value 0x%8.8" PRIx32
"", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1366 /* wait for and process debug entry */
1367 xscale_debug_entry(target
);
1369 LOG_DEBUG("disable single-step");
1370 xscale_disable_single_step(target
);
1372 LOG_DEBUG("set breakpoint at 0x%8.8" PRIx32
"", breakpoint
->address
);
1373 xscale_set_breakpoint(target
, breakpoint
);
1377 /* enable any pending breakpoints and watchpoints */
1378 xscale_enable_breakpoints(target
);
1379 xscale_enable_watchpoints(target
);
1381 /* restore banked registers */
1382 xscale_restore_context(target
);
1384 /* send resume request (command 0x30 or 0x31)
1385 * clean the trace buffer if it is to be enabled (0x62) */
1386 if (xscale
->trace
.buffer_enabled
)
1388 xscale_send_u32(target
, 0x62);
1389 xscale_send_u32(target
, 0x31);
1392 xscale_send_u32(target
, 0x30);
1395 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1396 LOG_DEBUG("writing cpsr with value 0x%8.8" PRIx32
"", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1398 for (i
= 7; i
>= 0; i
--)
1401 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1402 LOG_DEBUG("writing r%i with value 0x%8.8" PRIx32
"", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1406 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1407 LOG_DEBUG("writing PC with value 0x%8.8" PRIx32
"", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1409 target
->debug_reason
= DBG_REASON_NOTHALTED
;
1411 if (!debug_execution
)
1413 /* registers are now invalid */
1414 armv4_5_invalidate_core_regs(target
);
1415 target
->state
= TARGET_RUNNING
;
1416 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1420 target
->state
= TARGET_DEBUG_RUNNING
;
1421 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1424 LOG_DEBUG("target resumed");
1426 xscale
->handler_running
= 1;
1431 static int xscale_step_inner(struct target_s
*target
, int current
, uint32_t address
, int handle_breakpoints
)
1433 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1434 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1440 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1442 /* calculate PC of next instruction */
1443 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1445 uint32_t current_opcode
, current_pc
;
1446 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1448 target_read_u32(target
, current_pc
, ¤t_opcode
);
1449 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8" PRIx32
"", current_opcode
);
1453 LOG_DEBUG("enable single-step");
1454 if ((retval
=xscale_enable_single_step(target
, next_pc
)) != ERROR_OK
)
1457 /* restore banked registers */
1458 if ((retval
=xscale_restore_context(target
)) != ERROR_OK
)
1461 /* send resume request (command 0x30 or 0x31)
1462 * clean the trace buffer if it is to be enabled (0x62) */
1463 if (xscale
->trace
.buffer_enabled
)
1465 if ((retval
=xscale_send_u32(target
, 0x62)) != ERROR_OK
)
1467 if ((retval
=xscale_send_u32(target
, 0x31)) != ERROR_OK
)
1471 if ((retval
=xscale_send_u32(target
, 0x30)) != ERROR_OK
)
1475 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32))) != ERROR_OK
)
1477 LOG_DEBUG("writing cpsr with value 0x%8.8" PRIx32
"", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1479 for (i
= 7; i
>= 0; i
--)
1482 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32))) != ERROR_OK
)
1484 LOG_DEBUG("writing r%i with value 0x%8.8" PRIx32
"", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1488 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))) != ERROR_OK
)
1490 LOG_DEBUG("writing PC with value 0x%8.8" PRIx32
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1492 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1494 /* registers are now invalid */
1495 if ((retval
=armv4_5_invalidate_core_regs(target
)) != ERROR_OK
)
1498 /* wait for and process debug entry */
1499 if ((retval
=xscale_debug_entry(target
)) != ERROR_OK
)
1502 LOG_DEBUG("disable single-step");
1503 if ((retval
=xscale_disable_single_step(target
)) != ERROR_OK
)
1506 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1511 int xscale_step(struct target_s
*target
, int current
, uint32_t address
, int handle_breakpoints
)
1513 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1514 breakpoint_t
*breakpoint
= target
->breakpoints
;
1516 uint32_t current_pc
;
1519 if (target
->state
!= TARGET_HALTED
)
1521 LOG_WARNING("target not halted");
1522 return ERROR_TARGET_NOT_HALTED
;
1525 /* current = 1: continue on current pc, otherwise continue at <address> */
1527 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1529 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1531 /* if we're at the reset vector, we have to simulate the step */
1532 if (current_pc
== 0x0)
1534 if ((retval
=arm_simulate_step(target
, NULL
)) != ERROR_OK
)
1536 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1538 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1539 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1544 /* the front-end may request us not to handle breakpoints */
1545 if (handle_breakpoints
)
1546 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1548 if ((retval
=xscale_unset_breakpoint(target
, breakpoint
)) != ERROR_OK
)
1552 retval
= xscale_step_inner(target
, current
, address
, handle_breakpoints
);
1556 xscale_set_breakpoint(target
, breakpoint
);
1559 LOG_DEBUG("target stepped");
1565 int xscale_assert_reset(target_t
*target
)
1567 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1568 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1570 LOG_DEBUG("target->state: %s",
1571 Jim_Nvp_value2name_simple( nvp_target_state
, target
->state
)->name
);
1573 /* select DCSR instruction (set endstate to R-T-I to ensure we don't
1574 * end up in T-L-R, which would reset JTAG
1576 jtag_set_end_state(TAP_IDLE
);
1577 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
1579 /* set Hold reset, Halt mode and Trap Reset */
1580 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1581 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1582 xscale_write_dcsr(target
, 1, 0);
1584 /* select BYPASS, because having DCSR selected caused problems on the PXA27x */
1585 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, 0x7f);
1586 jtag_execute_queue();
1589 jtag_add_reset(0, 1);
1591 /* sleep 1ms, to be sure we fulfill any requirements */
1592 jtag_add_sleep(1000);
1593 jtag_execute_queue();
1595 target
->state
= TARGET_RESET
;
1597 if (target
->reset_halt
)
1600 if ((retval
= target_halt(target
)) != ERROR_OK
)
1607 int xscale_deassert_reset(target_t
*target
)
1609 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1610 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1612 fileio_t debug_handler
;
1614 uint32_t binary_size
;
1620 breakpoint_t
*breakpoint
= target
->breakpoints
;
1624 xscale
->ibcr_available
= 2;
1625 xscale
->ibcr0_used
= 0;
1626 xscale
->ibcr1_used
= 0;
1628 xscale
->dbr_available
= 2;
1629 xscale
->dbr0_used
= 0;
1630 xscale
->dbr1_used
= 0;
1632 /* mark all hardware breakpoints as unset */
1635 if (breakpoint
->type
== BKPT_HARD
)
1637 breakpoint
->set
= 0;
1639 breakpoint
= breakpoint
->next
;
1642 if (!xscale
->handler_installed
)
1645 jtag_add_reset(0, 0);
1647 /* wait 300ms; 150 and 100ms were not enough */
1648 jtag_add_sleep(300*1000);
1650 jtag_add_runtest(2030, jtag_set_end_state(TAP_IDLE
));
1651 jtag_execute_queue();
1653 /* set Hold reset, Halt mode and Trap Reset */
1654 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1655 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1656 xscale_write_dcsr(target
, 1, 0);
1658 /* Load debug handler */
1659 if (fileio_open(&debug_handler
, "xscale/debug_handler.bin", FILEIO_READ
, FILEIO_BINARY
) != ERROR_OK
)
1664 if ((binary_size
= debug_handler
.size
) % 4)
1666 LOG_ERROR("debug_handler.bin: size not a multiple of 4");
1670 if (binary_size
> 0x800)
1672 LOG_ERROR("debug_handler.bin: larger than 2kb");
1676 binary_size
= CEIL(binary_size
, 32) * 32;
1678 address
= xscale
->handler_address
;
1679 while (binary_size
> 0)
1681 uint32_t cache_line
[8];
1684 if ((retval
= fileio_read(&debug_handler
, 32, buffer
, &buf_cnt
)) != ERROR_OK
)
1689 for (i
= 0; i
< buf_cnt
; i
+= 4)
1691 /* convert LE buffer to host-endian uint32_t */
1692 cache_line
[i
/ 4] = le_to_h_u32(&buffer
[i
]);
1695 for (; buf_cnt
< 32; buf_cnt
+= 4)
1697 cache_line
[buf_cnt
/ 4] = 0xe1a08008;
1700 /* only load addresses other than the reset vectors */
1701 if ((address
% 0x400) != 0x0)
1703 xscale_load_ic(target
, 1, address
, cache_line
);
1707 binary_size
-= buf_cnt
;
1710 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
1711 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
1713 jtag_add_runtest(30, jtag_set_end_state(TAP_IDLE
));
1715 jtag_add_sleep(100000);
1717 /* set Hold reset, Halt mode and Trap Reset */
1718 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1719 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1720 xscale_write_dcsr(target
, 1, 0);
1722 /* clear Hold reset to let the target run (should enter debug handler) */
1723 xscale_write_dcsr(target
, 0, 1);
1724 target
->state
= TARGET_RUNNING
;
1726 if (!target
->reset_halt
)
1728 jtag_add_sleep(10000);
1730 /* we should have entered debug now */
1731 xscale_debug_entry(target
);
1732 target
->state
= TARGET_HALTED
;
1734 /* resume the target */
1735 xscale_resume(target
, 1, 0x0, 1, 0);
1738 fileio_close(&debug_handler
);
1742 jtag_add_reset(0, 0);
1748 int xscale_soft_reset_halt(struct target_s
*target
)
1753 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
)
1758 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, uint32_t value
)
1764 int xscale_full_context(target_t
*target
)
1766 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1774 if (target
->state
!= TARGET_HALTED
)
1776 LOG_WARNING("target not halted");
1777 return ERROR_TARGET_NOT_HALTED
;
1780 buffer
= malloc(4 * 8);
1782 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1783 * we can't enter User mode on an XScale (unpredictable),
1784 * but User shares registers with SYS
1786 for (i
= 1; i
< 7; i
++)
1790 /* check if there are invalid registers in the current mode
1792 for (j
= 0; j
<= 16; j
++)
1794 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
== 0)
1802 /* request banked registers */
1803 xscale_send_u32(target
, 0x0);
1806 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1807 tmp_cpsr
|= 0xc0; /* I/F bits */
1809 /* send CPSR for desired mode */
1810 xscale_send_u32(target
, tmp_cpsr
);
1812 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1813 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1815 xscale_receive(target
, buffer
, 8);
1816 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1817 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1818 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).valid
= 1;
1822 xscale_receive(target
, buffer
, 7);
1825 /* move data from buffer to register cache */
1826 for (j
= 8; j
<= 14; j
++)
1828 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]);
1829 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1830 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
= 1;
1840 int xscale_restore_context(target_t
*target
)
1842 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1848 if (target
->state
!= TARGET_HALTED
)
1850 LOG_WARNING("target not halted");
1851 return ERROR_TARGET_NOT_HALTED
;
1854 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1855 * we can't enter User mode on an XScale (unpredictable),
1856 * but User shares registers with SYS
1858 for (i
= 1; i
< 7; i
++)
1862 /* check if there are invalid registers in the current mode
1864 for (j
= 8; j
<= 14; j
++)
1866 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
== 1)
1870 /* if not USR/SYS, check if the SPSR needs to be written */
1871 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1873 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
== 1)
1881 /* send banked registers */
1882 xscale_send_u32(target
, 0x1);
1885 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1886 tmp_cpsr
|= 0xc0; /* I/F bits */
1888 /* send CPSR for desired mode */
1889 xscale_send_u32(target
, tmp_cpsr
);
1891 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1892 for (j
= 8; j
<= 14; j
++)
1894 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, j
).value
, 0, 32));
1895 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1898 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1900 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32));
1901 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1909 int xscale_read_memory(struct target_s
*target
, uint32_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
)
1911 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1912 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1917 LOG_DEBUG("address: 0x%8.8" PRIx32
", size: 0x%8.8" PRIx32
", count: 0x%8.8" PRIx32
, address
, size
, count
);
1919 if (target
->state
!= TARGET_HALTED
)
1921 LOG_WARNING("target not halted");
1922 return ERROR_TARGET_NOT_HALTED
;
1925 /* sanitize arguments */
1926 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1927 return ERROR_INVALID_ARGUMENTS
;
1929 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1930 return ERROR_TARGET_UNALIGNED_ACCESS
;
1932 /* send memory read request (command 0x1n, n: access size) */
1933 if ((retval
=xscale_send_u32(target
, 0x10 | size
)) != ERROR_OK
)
1936 /* send base address for read request */
1937 if ((retval
=xscale_send_u32(target
, address
)) != ERROR_OK
)
1940 /* send number of requested data words */
1941 if ((retval
=xscale_send_u32(target
, count
)) != ERROR_OK
)
1944 /* receive data from target (count times 32-bit words in host endianness) */
1945 buf32
= malloc(4 * count
);
1946 if ((retval
=xscale_receive(target
, buf32
, count
)) != ERROR_OK
)
1949 /* extract data from host-endian buffer into byte stream */
1950 for (i
= 0; i
< count
; i
++)
1955 target_buffer_set_u32(target
, buffer
, buf32
[i
]);
1959 target_buffer_set_u16(target
, buffer
, buf32
[i
] & 0xffff);
1963 *buffer
++ = buf32
[i
] & 0xff;
1966 LOG_ERROR("should never get here");
1973 /* examine DCSR, to see if Sticky Abort (SA) got set */
1974 if ((retval
=xscale_read_dcsr(target
)) != ERROR_OK
)
1976 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1979 if ((retval
=xscale_send_u32(target
, 0x60)) != ERROR_OK
)
1982 return ERROR_TARGET_DATA_ABORT
;
1988 int xscale_write_memory(struct target_s
*target
, uint32_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
)
1990 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1991 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1994 LOG_DEBUG("address: 0x%8.8" PRIx32
", size: 0x%8.8" PRIx32
", count: 0x%8.8" PRIx32
, address
, size
, count
);
1996 if (target
->state
!= TARGET_HALTED
)
1998 LOG_WARNING("target not halted");
1999 return ERROR_TARGET_NOT_HALTED
;
2002 /* sanitize arguments */
2003 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
2004 return ERROR_INVALID_ARGUMENTS
;
2006 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
2007 return ERROR_TARGET_UNALIGNED_ACCESS
;
2009 /* send memory write request (command 0x2n, n: access size) */
2010 if ((retval
=xscale_send_u32(target
, 0x20 | size
)) != ERROR_OK
)
2013 /* send base address for read request */
2014 if ((retval
=xscale_send_u32(target
, address
)) != ERROR_OK
)
2017 /* send number of requested data words to be written*/
2018 if ((retval
=xscale_send_u32(target
, count
)) != ERROR_OK
)
2021 /* extract data from host-endian buffer into byte stream */
2023 for (i
= 0; i
< count
; i
++)
2028 value
= target_buffer_get_u32(target
, buffer
);
2029 xscale_send_u32(target
, value
);
2033 value
= target_buffer_get_u16(target
, buffer
);
2034 xscale_send_u32(target
, value
);
2039 xscale_send_u32(target
, value
);
2043 LOG_ERROR("should never get here");
2048 if ((retval
=xscale_send(target
, buffer
, count
, size
)) != ERROR_OK
)
2051 /* examine DCSR, to see if Sticky Abort (SA) got set */
2052 if ((retval
=xscale_read_dcsr(target
)) != ERROR_OK
)
2054 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
2057 if ((retval
=xscale_send_u32(target
, 0x60)) != ERROR_OK
)
2060 return ERROR_TARGET_DATA_ABORT
;
2066 int xscale_bulk_write_memory(target_t
*target
, uint32_t address
, uint32_t count
, uint8_t *buffer
)
2068 return xscale_write_memory(target
, address
, 4, count
, buffer
);
2071 uint32_t xscale_get_ttb(target_t
*target
)
2073 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2074 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2077 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_TTB
]);
2078 ttb
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_TTB
].value
, 0, 32);
2083 void xscale_disable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2085 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2086 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2087 uint32_t cp15_control
;
2089 /* read cp15 control register */
2090 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2091 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2094 cp15_control
&= ~0x1U
;
2099 xscale_send_u32(target
, 0x50);
2100 xscale_send_u32(target
, xscale
->cache_clean_address
);
2102 /* invalidate DCache */
2103 xscale_send_u32(target
, 0x51);
2105 cp15_control
&= ~0x4U
;
2110 /* invalidate ICache */
2111 xscale_send_u32(target
, 0x52);
2112 cp15_control
&= ~0x1000U
;
2115 /* write new cp15 control register */
2116 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2118 /* execute cpwait to ensure outstanding operations complete */
2119 xscale_send_u32(target
, 0x53);
2122 void xscale_enable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2124 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2125 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2126 uint32_t cp15_control
;
2128 /* read cp15 control register */
2129 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2130 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2133 cp15_control
|= 0x1U
;
2136 cp15_control
|= 0x4U
;
2139 cp15_control
|= 0x1000U
;
2141 /* write new cp15 control register */
2142 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2144 /* execute cpwait to ensure outstanding operations complete */
2145 xscale_send_u32(target
, 0x53);
2148 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2151 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2152 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2154 if (target
->state
!= TARGET_HALTED
)
2156 LOG_WARNING("target not halted");
2157 return ERROR_TARGET_NOT_HALTED
;
2160 if (breakpoint
->set
)
2162 LOG_WARNING("breakpoint already set");
2166 if (breakpoint
->type
== BKPT_HARD
)
2168 uint32_t value
= breakpoint
->address
| 1;
2169 if (!xscale
->ibcr0_used
)
2171 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], value
);
2172 xscale
->ibcr0_used
= 1;
2173 breakpoint
->set
= 1; /* breakpoint set on first breakpoint register */
2175 else if (!xscale
->ibcr1_used
)
2177 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], value
);
2178 xscale
->ibcr1_used
= 1;
2179 breakpoint
->set
= 2; /* breakpoint set on second breakpoint register */
2183 LOG_ERROR("BUG: no hardware comparator available");
2187 else if (breakpoint
->type
== BKPT_SOFT
)
2189 if (breakpoint
->length
== 4)
2191 /* keep the original instruction in target endianness */
2192 if ((retval
= target_read_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2196 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2197 if ((retval
= target_write_u32(target
, breakpoint
->address
, xscale
->arm_bkpt
)) != ERROR_OK
)
2204 /* keep the original instruction in target endianness */
2205 if ((retval
= target_read_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2209 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2210 if ((retval
= target_write_u32(target
, breakpoint
->address
, xscale
->thumb_bkpt
)) != ERROR_OK
)
2215 breakpoint
->set
= 1;
2221 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2223 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2224 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2226 if (target
->state
!= TARGET_HALTED
)
2228 LOG_WARNING("target not halted");
2229 return ERROR_TARGET_NOT_HALTED
;
2232 if ((breakpoint
->type
== BKPT_HARD
) && (xscale
->ibcr_available
< 1))
2234 LOG_INFO("no breakpoint unit available for hardware breakpoint");
2235 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2238 if ((breakpoint
->length
!= 2) && (breakpoint
->length
!= 4))
2240 LOG_INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2241 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2244 if (breakpoint
->type
== BKPT_HARD
)
2246 xscale
->ibcr_available
--;
2252 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2255 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2256 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2258 if (target
->state
!= TARGET_HALTED
)
2260 LOG_WARNING("target not halted");
2261 return ERROR_TARGET_NOT_HALTED
;
2264 if (!breakpoint
->set
)
2266 LOG_WARNING("breakpoint not set");
2270 if (breakpoint
->type
== BKPT_HARD
)
2272 if (breakpoint
->set
== 1)
2274 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], 0x0);
2275 xscale
->ibcr0_used
= 0;
2277 else if (breakpoint
->set
== 2)
2279 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], 0x0);
2280 xscale
->ibcr1_used
= 0;
2282 breakpoint
->set
= 0;
2286 /* restore original instruction (kept in target endianness) */
2287 if (breakpoint
->length
== 4)
2289 if ((retval
= target_write_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2296 if ((retval
= target_write_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2301 breakpoint
->set
= 0;
2307 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2309 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2310 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2312 if (target
->state
!= TARGET_HALTED
)
2314 LOG_WARNING("target not halted");
2315 return ERROR_TARGET_NOT_HALTED
;
2318 if (breakpoint
->set
)
2320 xscale_unset_breakpoint(target
, breakpoint
);
2323 if (breakpoint
->type
== BKPT_HARD
)
2324 xscale
->ibcr_available
++;
2329 int xscale_set_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2331 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2332 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2334 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2335 uint32_t dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2337 if (target
->state
!= TARGET_HALTED
)
2339 LOG_WARNING("target not halted");
2340 return ERROR_TARGET_NOT_HALTED
;
2343 xscale_get_reg(dbcon
);
2345 switch (watchpoint
->rw
)
2357 LOG_ERROR("BUG: watchpoint->rw neither read, write nor access");
2360 if (!xscale
->dbr0_used
)
2362 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR0
], watchpoint
->address
);
2363 dbcon_value
|= enable
;
2364 xscale_set_reg_u32(dbcon
, dbcon_value
);
2365 watchpoint
->set
= 1;
2366 xscale
->dbr0_used
= 1;
2368 else if (!xscale
->dbr1_used
)
2370 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR1
], watchpoint
->address
);
2371 dbcon_value
|= enable
<< 2;
2372 xscale_set_reg_u32(dbcon
, dbcon_value
);
2373 watchpoint
->set
= 2;
2374 xscale
->dbr1_used
= 1;
2378 LOG_ERROR("BUG: no hardware comparator available");
2385 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2387 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2388 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2390 if (target
->state
!= TARGET_HALTED
)
2392 LOG_WARNING("target not halted");
2393 return ERROR_TARGET_NOT_HALTED
;
2396 if (xscale
->dbr_available
< 1)
2398 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2401 if ((watchpoint
->length
!= 1) && (watchpoint
->length
!= 2) && (watchpoint
->length
!= 4))
2403 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2406 xscale
->dbr_available
--;
2411 int xscale_unset_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2413 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2414 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2415 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2416 uint32_t dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2418 if (target
->state
!= TARGET_HALTED
)
2420 LOG_WARNING("target not halted");
2421 return ERROR_TARGET_NOT_HALTED
;
2424 if (!watchpoint
->set
)
2426 LOG_WARNING("breakpoint not set");
2430 if (watchpoint
->set
== 1)
2432 dbcon_value
&= ~0x3;
2433 xscale_set_reg_u32(dbcon
, dbcon_value
);
2434 xscale
->dbr0_used
= 0;
2436 else if (watchpoint
->set
== 2)
2438 dbcon_value
&= ~0xc;
2439 xscale_set_reg_u32(dbcon
, dbcon_value
);
2440 xscale
->dbr1_used
= 0;
2442 watchpoint
->set
= 0;
2447 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2449 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2450 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2452 if (target
->state
!= TARGET_HALTED
)
2454 LOG_WARNING("target not halted");
2455 return ERROR_TARGET_NOT_HALTED
;
2458 if (watchpoint
->set
)
2460 xscale_unset_watchpoint(target
, watchpoint
);
2463 xscale
->dbr_available
++;
2468 void xscale_enable_watchpoints(struct target_s
*target
)
2470 watchpoint_t
*watchpoint
= target
->watchpoints
;
2474 if (watchpoint
->set
== 0)
2475 xscale_set_watchpoint(target
, watchpoint
);
2476 watchpoint
= watchpoint
->next
;
2480 void xscale_enable_breakpoints(struct target_s
*target
)
2482 breakpoint_t
*breakpoint
= target
->breakpoints
;
2484 /* set any pending breakpoints */
2487 if (breakpoint
->set
== 0)
2488 xscale_set_breakpoint(target
, breakpoint
);
2489 breakpoint
= breakpoint
->next
;
2493 int xscale_get_reg(reg_t
*reg
)
2495 xscale_reg_t
*arch_info
= reg
->arch_info
;
2496 target_t
*target
= arch_info
->target
;
2497 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2498 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2500 /* DCSR, TX and RX are accessible via JTAG */
2501 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2503 return xscale_read_dcsr(arch_info
->target
);
2505 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2507 /* 1 = consume register content */
2508 return xscale_read_tx(arch_info
->target
, 1);
2510 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2512 /* can't read from RX register (host -> debug handler) */
2515 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2517 /* can't (explicitly) read from TXRXCTRL register */
2520 else /* Other DBG registers have to be transfered by the debug handler */
2522 /* send CP read request (command 0x40) */
2523 xscale_send_u32(target
, 0x40);
2525 /* send CP register number */
2526 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2528 /* read register value */
2529 xscale_read_tx(target
, 1);
2530 buf_cpy(xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
, reg
->value
, 32);
2539 int xscale_set_reg(reg_t
*reg
, uint8_t* buf
)
2541 xscale_reg_t
*arch_info
= reg
->arch_info
;
2542 target_t
*target
= arch_info
->target
;
2543 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2544 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2545 uint32_t value
= buf_get_u32(buf
, 0, 32);
2547 /* DCSR, TX and RX are accessible via JTAG */
2548 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2550 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32, value
);
2551 return xscale_write_dcsr(arch_info
->target
, -1, -1);
2553 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2555 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
2556 return xscale_write_rx(arch_info
->target
);
2558 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2560 /* can't write to TX register (debug-handler -> host) */
2563 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2565 /* can't (explicitly) write to TXRXCTRL register */
2568 else /* Other DBG registers have to be transfered by the debug handler */
2570 /* send CP write request (command 0x41) */
2571 xscale_send_u32(target
, 0x41);
2573 /* send CP register number */
2574 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2576 /* send CP register value */
2577 xscale_send_u32(target
, value
);
2578 buf_set_u32(reg
->value
, 0, 32, value
);
2584 /* convenience wrapper to access XScale specific registers */
2585 int xscale_set_reg_u32(reg_t
*reg
, uint32_t value
)
2589 buf_set_u32(buf
, 0, 32, value
);
2591 return xscale_set_reg(reg
, buf
);
2594 int xscale_write_dcsr_sw(target_t
*target
, uint32_t value
)
2596 /* get pointers to arch-specific information */
2597 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2598 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2599 reg_t
*dcsr
= &xscale
->reg_cache
->reg_list
[XSCALE_DCSR
];
2600 xscale_reg_t
*dcsr_arch_info
= dcsr
->arch_info
;
2602 /* send CP write request (command 0x41) */
2603 xscale_send_u32(target
, 0x41);
2605 /* send CP register number */
2606 xscale_send_u32(target
, dcsr_arch_info
->dbg_handler_number
);
2608 /* send CP register value */
2609 xscale_send_u32(target
, value
);
2610 buf_set_u32(dcsr
->value
, 0, 32, value
);
2615 int xscale_read_trace(target_t
*target
)
2617 /* get pointers to arch-specific information */
2618 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2619 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2620 xscale_trace_data_t
**trace_data_p
;
2622 /* 258 words from debug handler
2623 * 256 trace buffer entries
2624 * 2 checkpoint addresses
2626 uint32_t trace_buffer
[258];
2627 int is_address
[256];
2630 if (target
->state
!= TARGET_HALTED
)
2632 LOG_WARNING("target must be stopped to read trace data");
2633 return ERROR_TARGET_NOT_HALTED
;
2636 /* send read trace buffer command (command 0x61) */
2637 xscale_send_u32(target
, 0x61);
2639 /* receive trace buffer content */
2640 xscale_receive(target
, trace_buffer
, 258);
2642 /* parse buffer backwards to identify address entries */
2643 for (i
= 255; i
>= 0; i
--)
2646 if (((trace_buffer
[i
] & 0xf0) == 0x90) ||
2647 ((trace_buffer
[i
] & 0xf0) == 0xd0))
2650 is_address
[--i
] = 1;
2652 is_address
[--i
] = 1;
2654 is_address
[--i
] = 1;
2656 is_address
[--i
] = 1;
2661 /* search first non-zero entry */
2662 for (j
= 0; (j
< 256) && (trace_buffer
[j
] == 0) && (!is_address
[j
]); j
++)
2667 LOG_DEBUG("no trace data collected");
2668 return ERROR_XSCALE_NO_TRACE_DATA
;
2671 for (trace_data_p
= &xscale
->trace
.data
; *trace_data_p
; trace_data_p
= &(*trace_data_p
)->next
)
2674 *trace_data_p
= malloc(sizeof(xscale_trace_data_t
));
2675 (*trace_data_p
)->next
= NULL
;
2676 (*trace_data_p
)->chkpt0
= trace_buffer
[256];
2677 (*trace_data_p
)->chkpt1
= trace_buffer
[257];
2678 (*trace_data_p
)->last_instruction
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
2679 (*trace_data_p
)->entries
= malloc(sizeof(xscale_trace_entry_t
) * (256 - j
));
2680 (*trace_data_p
)->depth
= 256 - j
;
2682 for (i
= j
; i
< 256; i
++)
2684 (*trace_data_p
)->entries
[i
- j
].data
= trace_buffer
[i
];
2686 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_ADDRESS
;
2688 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_MESSAGE
;
2694 int xscale_read_instruction(target_t
*target
, arm_instruction_t
*instruction
)
2696 /* get pointers to arch-specific information */
2697 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2698 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2705 if (!xscale
->trace
.image
)
2706 return ERROR_TRACE_IMAGE_UNAVAILABLE
;
2708 /* search for the section the current instruction belongs to */
2709 for (i
= 0; i
< xscale
->trace
.image
->num_sections
; i
++)
2711 if ((xscale
->trace
.image
->sections
[i
].base_address
<= xscale
->trace
.current_pc
) &&
2712 (xscale
->trace
.image
->sections
[i
].base_address
+ xscale
->trace
.image
->sections
[i
].size
> xscale
->trace
.current_pc
))
2721 /* current instruction couldn't be found in the image */
2722 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2725 if (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
)
2728 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2729 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2730 4, buf
, &size_read
)) != ERROR_OK
)
2732 LOG_ERROR("error while reading instruction: %i", retval
);
2733 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2735 opcode
= target_buffer_get_u32(target
, buf
);
2736 arm_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2738 else if (xscale
->trace
.core_state
== ARMV4_5_STATE_THUMB
)
2741 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2742 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2743 2, buf
, &size_read
)) != ERROR_OK
)
2745 LOG_ERROR("error while reading instruction: %i", retval
);
2746 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2748 opcode
= target_buffer_get_u16(target
, buf
);
2749 thumb_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2753 LOG_ERROR("BUG: unknown core state encountered");
2760 int xscale_branch_address(xscale_trace_data_t
*trace_data
, int i
, uint32_t *target
)
2762 /* if there are less than four entries prior to the indirect branch message
2763 * we can't extract the address */
2769 *target
= (trace_data
->entries
[i
-1].data
) | (trace_data
->entries
[i
-2].data
<< 8) |
2770 (trace_data
->entries
[i
-3].data
<< 16) | (trace_data
->entries
[i
-4].data
<< 24);
2775 int xscale_analyze_trace(target_t
*target
, command_context_t
*cmd_ctx
)
2777 /* get pointers to arch-specific information */
2778 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2779 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2781 uint32_t next_pc
= 0x0;
2782 xscale_trace_data_t
*trace_data
= xscale
->trace
.data
;
2791 xscale
->trace
.core_state
= ARMV4_5_STATE_ARM
;
2796 for (i
= 0; i
< trace_data
->depth
; i
++)
2802 if (trace_data
->entries
[i
].type
== XSCALE_TRACE_ADDRESS
)
2805 switch ((trace_data
->entries
[i
].data
& 0xf0) >> 4)
2807 case 0: /* Exceptions */
2815 exception
= (trace_data
->entries
[i
].data
& 0x70) >> 4;
2817 next_pc
= (trace_data
->entries
[i
].data
& 0xf0) >> 2;
2818 command_print(cmd_ctx
, "--- exception %i ---", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2820 case 8: /* Direct Branch */
2823 case 9: /* Indirect Branch */
2825 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2830 case 13: /* Checkpointed Indirect Branch */
2831 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2834 if (((chkpt
== 0) && (next_pc
!= trace_data
->chkpt0
))
2835 || ((chkpt
== 1) && (next_pc
!= trace_data
->chkpt1
)))
2836 LOG_WARNING("checkpointed indirect branch target address doesn't match checkpoint");
2838 /* explicit fall-through */
2839 case 12: /* Checkpointed Direct Branch */
2844 next_pc
= trace_data
->chkpt0
;
2847 else if (chkpt
== 1)
2850 next_pc
= trace_data
->chkpt0
;
2855 LOG_WARNING("more than two checkpointed branches encountered");
2858 case 15: /* Roll-over */
2861 default: /* Reserved */
2862 command_print(cmd_ctx
, "--- reserved trace message ---");
2863 LOG_ERROR("BUG: trace message %i is reserved", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2867 if (xscale
->trace
.pc_ok
)
2869 int executed
= (trace_data
->entries
[i
].data
& 0xf) + rollover
* 16;
2870 arm_instruction_t instruction
;
2872 if ((exception
== 6) || (exception
== 7))
2874 /* IRQ or FIQ exception, no instruction executed */
2878 while (executed
-- >= 0)
2880 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2882 /* can't continue tracing with no image available */
2883 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2887 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2889 /* TODO: handle incomplete images */
2893 /* a precise abort on a load to the PC is included in the incremental
2894 * word count, other instructions causing data aborts are not included
2896 if ((executed
== 0) && (exception
== 4)
2897 && ((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDM
)))
2899 if ((instruction
.type
== ARM_LDM
)
2900 && ((instruction
.info
.load_store_multiple
.register_list
& 0x8000) == 0))
2904 else if (((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDRSH
))
2905 && (instruction
.info
.load_store
.Rd
!= 15))
2911 /* only the last instruction executed
2912 * (the one that caused the control flow change)
2913 * could be a taken branch
2915 if (((executed
== -1) && (branch
== 1)) &&
2916 (((instruction
.type
== ARM_B
) ||
2917 (instruction
.type
== ARM_BL
) ||
2918 (instruction
.type
== ARM_BLX
)) &&
2919 (instruction
.info
.b_bl_bx_blx
.target_address
!= 0xffffffff)))
2921 xscale
->trace
.current_pc
= instruction
.info
.b_bl_bx_blx
.target_address
;
2925 xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2;
2927 command_print(cmd_ctx
, "%s", instruction
.text
);
2935 xscale
->trace
.current_pc
= next_pc
;
2936 xscale
->trace
.pc_ok
= 1;
2940 for (; xscale
->trace
.current_pc
< trace_data
->last_instruction
; xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2)
2942 arm_instruction_t instruction
;
2943 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2945 /* can't continue tracing with no image available */
2946 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2950 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2952 /* TODO: handle incomplete images */
2955 command_print(cmd_ctx
, "%s", instruction
.text
);
2958 trace_data
= trace_data
->next
;
2964 void xscale_build_reg_cache(target_t
*target
)
2966 /* get pointers to arch-specific information */
2967 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2968 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2970 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
2971 xscale_reg_t
*arch_info
= malloc(sizeof(xscale_reg_arch_info
));
2973 int num_regs
= sizeof(xscale_reg_arch_info
) / sizeof(xscale_reg_t
);
2975 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
2976 armv4_5
->core_cache
= (*cache_p
);
2978 /* register a register arch-type for XScale dbg registers only once */
2979 if (xscale_reg_arch_type
== -1)
2980 xscale_reg_arch_type
= register_reg_arch_type(xscale_get_reg
, xscale_set_reg
);
2982 (*cache_p
)->next
= malloc(sizeof(reg_cache_t
));
2983 cache_p
= &(*cache_p
)->next
;
2985 /* fill in values for the xscale reg cache */
2986 (*cache_p
)->name
= "XScale registers";
2987 (*cache_p
)->next
= NULL
;
2988 (*cache_p
)->reg_list
= malloc(num_regs
* sizeof(reg_t
));
2989 (*cache_p
)->num_regs
= num_regs
;
2991 for (i
= 0; i
< num_regs
; i
++)
2993 (*cache_p
)->reg_list
[i
].name
= xscale_reg_list
[i
];
2994 (*cache_p
)->reg_list
[i
].value
= calloc(4, 1);
2995 (*cache_p
)->reg_list
[i
].dirty
= 0;
2996 (*cache_p
)->reg_list
[i
].valid
= 0;
2997 (*cache_p
)->reg_list
[i
].size
= 32;
2998 (*cache_p
)->reg_list
[i
].bitfield_desc
= NULL
;
2999 (*cache_p
)->reg_list
[i
].num_bitfields
= 0;
3000 (*cache_p
)->reg_list
[i
].arch_info
= &arch_info
[i
];
3001 (*cache_p
)->reg_list
[i
].arch_type
= xscale_reg_arch_type
;
3002 arch_info
[i
] = xscale_reg_arch_info
[i
];
3003 arch_info
[i
].target
= target
;
3006 xscale
->reg_cache
= (*cache_p
);
3009 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
3014 int xscale_quit(void)
3019 int xscale_init_arch_info(target_t
*target
, xscale_common_t
*xscale
, jtag_tap_t
*tap
, const char *variant
)
3021 armv4_5_common_t
*armv4_5
;
3022 uint32_t high_reset_branch
, low_reset_branch
;
3025 armv4_5
= &xscale
->armv4_5_common
;
3027 /* store architecture specfic data (none so far) */
3028 xscale
->arch_info
= NULL
;
3029 xscale
->common_magic
= XSCALE_COMMON_MAGIC
;
3031 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
3032 xscale
->variant
= strdup(variant
);
3034 /* prepare JTAG information for the new target */
3035 xscale
->jtag_info
.tap
= tap
;
3037 xscale
->jtag_info
.dbgrx
= 0x02;
3038 xscale
->jtag_info
.dbgtx
= 0x10;
3039 xscale
->jtag_info
.dcsr
= 0x09;
3040 xscale
->jtag_info
.ldic
= 0x07;
3042 if ((strcmp(xscale
->variant
, "pxa250") == 0) ||
3043 (strcmp(xscale
->variant
, "pxa255") == 0) ||
3044 (strcmp(xscale
->variant
, "pxa26x") == 0))
3046 xscale
->jtag_info
.ir_length
= 5;
3048 else if ((strcmp(xscale
->variant
, "pxa27x") == 0) ||
3049 (strcmp(xscale
->variant
, "ixp42x") == 0) ||
3050 (strcmp(xscale
->variant
, "ixp45x") == 0) ||
3051 (strcmp(xscale
->variant
, "ixp46x") == 0))
3053 xscale
->jtag_info
.ir_length
= 7;
3056 /* the debug handler isn't installed (and thus not running) at this time */
3057 xscale
->handler_installed
= 0;
3058 xscale
->handler_running
= 0;
3059 xscale
->handler_address
= 0xfe000800;
3061 /* clear the vectors we keep locally for reference */
3062 memset(xscale
->low_vectors
, 0, sizeof(xscale
->low_vectors
));
3063 memset(xscale
->high_vectors
, 0, sizeof(xscale
->high_vectors
));
3065 /* no user-specified vectors have been configured yet */
3066 xscale
->static_low_vectors_set
= 0x0;
3067 xscale
->static_high_vectors_set
= 0x0;
3069 /* calculate branches to debug handler */
3070 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
3071 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
3073 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
3074 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
3076 for (i
= 1; i
<= 7; i
++)
3078 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3079 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3082 /* 64kB aligned region used for DCache cleaning */
3083 xscale
->cache_clean_address
= 0xfffe0000;
3085 xscale
->hold_rst
= 0;
3086 xscale
->external_debug_break
= 0;
3088 xscale
->ibcr_available
= 2;
3089 xscale
->ibcr0_used
= 0;
3090 xscale
->ibcr1_used
= 0;
3092 xscale
->dbr_available
= 2;
3093 xscale
->dbr0_used
= 0;
3094 xscale
->dbr1_used
= 0;
3096 xscale
->arm_bkpt
= ARMV5_BKPT(0x0);
3097 xscale
->thumb_bkpt
= ARMV5_T_BKPT(0x0) & 0xffff;
3099 xscale
->vector_catch
= 0x1;
3101 xscale
->trace
.capture_status
= TRACE_IDLE
;
3102 xscale
->trace
.data
= NULL
;
3103 xscale
->trace
.image
= NULL
;
3104 xscale
->trace
.buffer_enabled
= 0;
3105 xscale
->trace
.buffer_fill
= 0;
3107 /* prepare ARMv4/5 specific information */
3108 armv4_5
->arch_info
= xscale
;
3109 armv4_5
->read_core_reg
= xscale_read_core_reg
;
3110 armv4_5
->write_core_reg
= xscale_write_core_reg
;
3111 armv4_5
->full_context
= xscale_full_context
;
3113 armv4_5_init_arch_info(target
, armv4_5
);
3115 xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
= -1;
3116 xscale
->armv4_5_mmu
.get_ttb
= xscale_get_ttb
;
3117 xscale
->armv4_5_mmu
.read_memory
= xscale_read_memory
;
3118 xscale
->armv4_5_mmu
.write_memory
= xscale_write_memory
;
3119 xscale
->armv4_5_mmu
.disable_mmu_caches
= xscale_disable_mmu_caches
;
3120 xscale
->armv4_5_mmu
.enable_mmu_caches
= xscale_enable_mmu_caches
;
3121 xscale
->armv4_5_mmu
.has_tiny_pages
= 1;
3122 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3127 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
3128 int xscale_target_create(struct target_s
*target
, Jim_Interp
*interp
)
3130 xscale_common_t
*xscale
= calloc(1,sizeof(xscale_common_t
));
3132 xscale_init_arch_info(target
, xscale
, target
->tap
, target
->variant
);
3133 xscale_build_reg_cache(target
);
3138 int xscale_handle_debug_handler_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3140 target_t
*target
= NULL
;
3141 armv4_5_common_t
*armv4_5
;
3142 xscale_common_t
*xscale
;
3144 uint32_t handler_address
;
3148 LOG_ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
3152 if ((target
= get_target(args
[0])) == NULL
)
3154 LOG_ERROR("target '%s' not defined", args
[0]);
3158 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3163 handler_address
= strtoul(args
[1], NULL
, 0);
3165 if (((handler_address
>= 0x800) && (handler_address
<= 0x1fef800)) ||
3166 ((handler_address
>= 0xfe000800) && (handler_address
<= 0xfffff800)))
3168 xscale
->handler_address
= handler_address
;
3172 LOG_ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
3179 int xscale_handle_cache_clean_address_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3181 target_t
*target
= NULL
;
3182 armv4_5_common_t
*armv4_5
;
3183 xscale_common_t
*xscale
;
3185 uint32_t cache_clean_address
;
3189 return ERROR_COMMAND_SYNTAX_ERROR
;
3192 target
= get_target(args
[0]);
3195 LOG_ERROR("target '%s' not defined", args
[0]);
3199 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3204 cache_clean_address
= strtoul(args
[1], NULL
, 0);
3206 if (cache_clean_address
& 0xffff)
3208 LOG_ERROR("xscale cache_clean_address <address> must be 64kb aligned");
3212 xscale
->cache_clean_address
= cache_clean_address
;
3218 int xscale_handle_cache_info_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3220 target_t
*target
= get_current_target(cmd_ctx
);
3221 armv4_5_common_t
*armv4_5
;
3222 xscale_common_t
*xscale
;
3224 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3229 return armv4_5_handle_cache_info_command(cmd_ctx
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
3232 static int xscale_virt2phys(struct target_s
*target
, uint32_t virtual, uint32_t *physical
)
3234 armv4_5_common_t
*armv4_5
;
3235 xscale_common_t
*xscale
;
3242 if ((retval
= xscale_get_arch_pointers(target
, &armv4_5
, &xscale
)) != ERROR_OK
)
3246 uint32_t ret
= armv4_5_mmu_translate_va(target
, &xscale
->armv4_5_mmu
, virtual, &type
, &cb
, &domain
, &ap
);
3255 static int xscale_mmu(struct target_s
*target
, int *enabled
)
3257 armv4_5_common_t
*armv4_5
= target
->arch_info
;
3258 xscale_common_t
*xscale
= armv4_5
->arch_info
;
3260 if (target
->state
!= TARGET_HALTED
)
3262 LOG_ERROR("Target not halted");
3263 return ERROR_TARGET_INVALID
;
3265 *enabled
= xscale
->armv4_5_mmu
.mmu_enabled
;
3269 int xscale_handle_mmu_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3271 target_t
*target
= get_current_target(cmd_ctx
);
3272 armv4_5_common_t
*armv4_5
;
3273 xscale_common_t
*xscale
;
3275 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3280 if (target
->state
!= TARGET_HALTED
)
3282 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3288 if (strcmp("enable", args
[0]) == 0)
3290 xscale_enable_mmu_caches(target
, 1, 0, 0);
3291 xscale
->armv4_5_mmu
.mmu_enabled
= 1;
3293 else if (strcmp("disable", args
[0]) == 0)
3295 xscale_disable_mmu_caches(target
, 1, 0, 0);
3296 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3300 command_print(cmd_ctx
, "mmu %s", (xscale
->armv4_5_mmu
.mmu_enabled
) ? "enabled" : "disabled");
3305 int xscale_handle_idcache_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3307 target_t
*target
= get_current_target(cmd_ctx
);
3308 armv4_5_common_t
*armv4_5
;
3309 xscale_common_t
*xscale
;
3310 int icache
= 0, dcache
= 0;
3312 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3317 if (target
->state
!= TARGET_HALTED
)
3319 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3323 if (strcmp(cmd
, "icache") == 0)
3325 else if (strcmp(cmd
, "dcache") == 0)
3330 if (strcmp("enable", args
[0]) == 0)
3332 xscale_enable_mmu_caches(target
, 0, dcache
, icache
);
3335 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 1;
3337 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 1;
3339 else if (strcmp("disable", args
[0]) == 0)
3341 xscale_disable_mmu_caches(target
, 0, dcache
, icache
);
3344 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 0;
3346 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 0;
3351 command_print(cmd_ctx
, "icache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
) ? "enabled" : "disabled");
3354 command_print(cmd_ctx
, "dcache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
) ? "enabled" : "disabled");
3359 int xscale_handle_vector_catch_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3361 target_t
*target
= get_current_target(cmd_ctx
);
3362 armv4_5_common_t
*armv4_5
;
3363 xscale_common_t
*xscale
;
3365 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3372 command_print(cmd_ctx
, "usage: xscale vector_catch [mask]");
3376 xscale
->vector_catch
= strtoul(args
[0], NULL
, 0);
3377 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 8, xscale
->vector_catch
);
3378 xscale_write_dcsr(target
, -1, -1);
3381 command_print(cmd_ctx
, "vector catch mask: 0x%2.2x", xscale
->vector_catch
);
3387 int xscale_handle_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3389 target_t
*target
= get_current_target(cmd_ctx
);
3390 armv4_5_common_t
*armv4_5
;
3391 xscale_common_t
*xscale
;
3392 uint32_t dcsr_value
;
3394 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3399 if (target
->state
!= TARGET_HALTED
)
3401 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3405 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3407 xscale_trace_data_t
*td
, *next_td
;
3408 xscale
->trace
.buffer_enabled
= 1;
3410 /* free old trace data */
3411 td
= xscale
->trace
.data
;
3421 xscale
->trace
.data
= NULL
;
3423 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3425 xscale
->trace
.buffer_enabled
= 0;
3428 if ((argc
>= 2) && (strcmp("fill", args
[1]) == 0))
3431 xscale
->trace
.buffer_fill
= strtoul(args
[2], NULL
, 0);
3433 xscale
->trace
.buffer_fill
= 1;
3435 else if ((argc
>= 2) && (strcmp("wrap", args
[1]) == 0))
3437 xscale
->trace
.buffer_fill
= -1;
3440 if (xscale
->trace
.buffer_enabled
)
3442 /* if we enable the trace buffer in fill-once
3443 * mode we know the address of the first instruction */
3444 xscale
->trace
.pc_ok
= 1;
3445 xscale
->trace
.current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
3449 /* otherwise the address is unknown, and we have no known good PC */
3450 xscale
->trace
.pc_ok
= 0;
3453 command_print(cmd_ctx
, "trace buffer %s (%s)",
3454 (xscale
->trace
.buffer_enabled
) ? "enabled" : "disabled",
3455 (xscale
->trace
.buffer_fill
> 0) ? "fill" : "wrap");
3457 dcsr_value
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32);
3458 if (xscale
->trace
.buffer_fill
>= 0)
3459 xscale_write_dcsr_sw(target
, (dcsr_value
& 0xfffffffc) | 2);
3461 xscale_write_dcsr_sw(target
, dcsr_value
& 0xfffffffc);
3466 int xscale_handle_trace_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3469 armv4_5_common_t
*armv4_5
;
3470 xscale_common_t
*xscale
;
3474 command_print(cmd_ctx
, "usage: xscale trace_image <file> [base address] [type]");
3478 target
= get_current_target(cmd_ctx
);
3480 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3485 if (xscale
->trace
.image
)
3487 image_close(xscale
->trace
.image
);
3488 free(xscale
->trace
.image
);
3489 command_print(cmd_ctx
, "previously loaded image found and closed");
3492 xscale
->trace
.image
= malloc(sizeof(image_t
));
3493 xscale
->trace
.image
->base_address_set
= 0;
3494 xscale
->trace
.image
->start_address_set
= 0;
3496 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
3499 xscale
->trace
.image
->base_address_set
= 1;
3500 xscale
->trace
.image
->base_address
= strtoul(args
[1], NULL
, 0);
3504 xscale
->trace
.image
->base_address_set
= 0;
3507 if (image_open(xscale
->trace
.image
, args
[0], (argc
>= 3) ? args
[2] : NULL
) != ERROR_OK
)
3509 free(xscale
->trace
.image
);
3510 xscale
->trace
.image
= NULL
;
3517 int xscale_handle_dump_trace_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3519 target_t
*target
= get_current_target(cmd_ctx
);
3520 armv4_5_common_t
*armv4_5
;
3521 xscale_common_t
*xscale
;
3522 xscale_trace_data_t
*trace_data
;
3525 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3530 if (target
->state
!= TARGET_HALTED
)
3532 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3538 command_print(cmd_ctx
, "usage: xscale dump_trace <file>");
3542 trace_data
= xscale
->trace
.data
;
3546 command_print(cmd_ctx
, "no trace data collected");
3550 if (fileio_open(&file
, args
[0], FILEIO_WRITE
, FILEIO_BINARY
) != ERROR_OK
)
3559 fileio_write_u32(&file
, trace_data
->chkpt0
);
3560 fileio_write_u32(&file
, trace_data
->chkpt1
);
3561 fileio_write_u32(&file
, trace_data
->last_instruction
);
3562 fileio_write_u32(&file
, trace_data
->depth
);
3564 for (i
= 0; i
< trace_data
->depth
; i
++)
3565 fileio_write_u32(&file
, trace_data
->entries
[i
].data
| ((trace_data
->entries
[i
].type
& 0xffff) << 16));
3567 trace_data
= trace_data
->next
;
3570 fileio_close(&file
);
3575 int xscale_handle_analyze_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3577 target_t
*target
= get_current_target(cmd_ctx
);
3578 armv4_5_common_t
*armv4_5
;
3579 xscale_common_t
*xscale
;
3581 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3586 xscale_analyze_trace(target
, cmd_ctx
);
3591 int xscale_handle_cp15(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3593 target_t
*target
= get_current_target(cmd_ctx
);
3594 armv4_5_common_t
*armv4_5
;
3595 xscale_common_t
*xscale
;
3597 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3602 if (target
->state
!= TARGET_HALTED
)
3604 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3607 uint32_t reg_no
= 0;
3611 reg_no
= strtoul(args
[0], NULL
, 0);
3612 /*translate from xscale cp15 register no to openocd register*/
3616 reg_no
= XSCALE_MAINID
;
3619 reg_no
= XSCALE_CTRL
;
3622 reg_no
= XSCALE_TTB
;
3625 reg_no
= XSCALE_DAC
;
3628 reg_no
= XSCALE_FSR
;
3631 reg_no
= XSCALE_FAR
;
3634 reg_no
= XSCALE_PID
;
3637 reg_no
= XSCALE_CPACCESS
;
3640 command_print(cmd_ctx
, "invalid register number");
3641 return ERROR_INVALID_ARGUMENTS
;
3643 reg
= &xscale
->reg_cache
->reg_list
[reg_no
];
3650 /* read cp15 control register */
3651 xscale_get_reg(reg
);
3652 value
= buf_get_u32(reg
->value
, 0, 32);
3653 command_print(cmd_ctx
, "%s (/%i): 0x%" PRIx32
"", reg
->name
, (int)(reg
->size
), value
);
3658 uint32_t value
= strtoul(args
[1], NULL
, 0);
3660 /* send CP write request (command 0x41) */
3661 xscale_send_u32(target
, 0x41);
3663 /* send CP register number */
3664 xscale_send_u32(target
, reg_no
);
3666 /* send CP register value */
3667 xscale_send_u32(target
, value
);
3669 /* execute cpwait to ensure outstanding operations complete */
3670 xscale_send_u32(target
, 0x53);
3674 command_print(cmd_ctx
, "usage: cp15 [register]<, [value]>");
3680 int xscale_register_commands(struct command_context_s
*cmd_ctx
)
3682 command_t
*xscale_cmd
;
3684 xscale_cmd
= register_command(cmd_ctx
, NULL
, "xscale", NULL
, COMMAND_ANY
, "xscale specific commands");
3686 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");
3687 register_command(cmd_ctx
, xscale_cmd
, "cache_clean_address", xscale_handle_cache_clean_address_command
, COMMAND_ANY
, NULL
);
3689 register_command(cmd_ctx
, xscale_cmd
, "cache_info", xscale_handle_cache_info_command
, COMMAND_EXEC
, NULL
);
3690 register_command(cmd_ctx
, xscale_cmd
, "mmu", xscale_handle_mmu_command
, COMMAND_EXEC
, "['enable'|'disable'] the MMU");
3691 register_command(cmd_ctx
, xscale_cmd
, "icache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the ICache");
3692 register_command(cmd_ctx
, xscale_cmd
, "dcache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the DCache");
3694 register_command(cmd_ctx
, xscale_cmd
, "vector_catch", xscale_handle_vector_catch_command
, COMMAND_EXEC
, "<mask> of vectors that should be catched");
3696 register_command(cmd_ctx
, xscale_cmd
, "trace_buffer", xscale_handle_trace_buffer_command
, COMMAND_EXEC
, "<enable|disable> ['fill' [n]|'wrap']");
3698 register_command(cmd_ctx
, xscale_cmd
, "dump_trace", xscale_handle_dump_trace_command
, COMMAND_EXEC
, "dump content of trace buffer to <file>");
3699 register_command(cmd_ctx
, xscale_cmd
, "analyze_trace", xscale_handle_analyze_trace_buffer_command
, COMMAND_EXEC
, "analyze content of trace buffer");
3700 register_command(cmd_ctx
, xscale_cmd
, "trace_image", xscale_handle_trace_image_command
,
3701 COMMAND_EXEC
, "load image from <file> [base address]");
3703 register_command(cmd_ctx
, xscale_cmd
, "cp15", xscale_handle_cp15
, COMMAND_EXEC
, "access coproc 15 <register> [value]");
3705 armv4_5_register_commands(cmd_ctx
);