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
);
Linking to existing account procedure
If you already have an account and want to add another login method
you
MUST first sign in with your existing account and
then change URL to read
https://review.openocd.org/login/?link
to get to this page again but this time it'll work for linking. Thank you.
SSH host keys fingerprints
1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=.. |
|+o.. . |
|*.o . . |
|+B . . . |
|Bo. = o S |
|Oo.+ + = |
|oB=.* = . o |
| =+=.+ + E |
|. .=o . o |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)