1 /***************************************************************************
2 * Copyright (C) 2006, 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
24 #include "replacements.h"
31 #include "arm_simulator.h"
32 #include "arm_disassembler.h"
35 #include "binarybuffer.h"
36 #include "time_support.h"
37 #include "breakpoints.h"
43 #include <sys/types.h>
49 int xscale_register_commands(struct command_context_s
*cmd_ctx
);
51 /* forward declarations */
52 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
);
53 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
56 int xscale_arch_state(struct target_s
*target
);
57 int xscale_poll(target_t
*target
);
58 int xscale_halt(target_t
*target
);
59 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
);
60 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
);
61 int xscale_debug_entry(target_t
*target
);
62 int xscale_restore_context(target_t
*target
);
64 int xscale_assert_reset(target_t
*target
);
65 int xscale_deassert_reset(target_t
*target
);
66 int xscale_soft_reset_halt(struct target_s
*target
);
68 int xscale_set_reg_u32(reg_t
*reg
, u32 value
);
70 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
);
71 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
);
73 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
74 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
75 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
);
76 int xscale_checksum_memory(struct target_s
*target
, u32 address
, u32 count
, u32
* checksum
);
78 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
79 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
80 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
81 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
82 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
83 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
84 void xscale_enable_watchpoints(struct target_s
*target
);
85 void xscale_enable_breakpoints(struct target_s
*target
);
86 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
);
87 static int xscale_mmu(struct target_s
*target
, int *enabled
);
89 int xscale_read_trace(target_t
*target
);
91 target_type_t xscale_target
=
96 .arch_state
= xscale_arch_state
,
98 .target_request_data
= NULL
,
101 .resume
= xscale_resume
,
104 .assert_reset
= xscale_assert_reset
,
105 .deassert_reset
= xscale_deassert_reset
,
106 .soft_reset_halt
= xscale_soft_reset_halt
,
108 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
110 .read_memory
= xscale_read_memory
,
111 .write_memory
= xscale_write_memory
,
112 .bulk_write_memory
= xscale_bulk_write_memory
,
113 .checksum_memory
= xscale_checksum_memory
,
114 .blank_check_memory
= NULL
,
116 .run_algorithm
= armv4_5_run_algorithm
,
118 .add_breakpoint
= xscale_add_breakpoint
,
119 .remove_breakpoint
= xscale_remove_breakpoint
,
120 .add_watchpoint
= xscale_add_watchpoint
,
121 .remove_watchpoint
= xscale_remove_watchpoint
,
123 .register_commands
= xscale_register_commands
,
124 .target_command
= xscale_target_command
,
125 .init_target
= xscale_init_target
,
128 .virt2phys
= xscale_virt2phys
,
132 char* xscale_reg_list
[] =
134 "XSCALE_MAINID", /* 0 */
144 "XSCALE_IBCR0", /* 10 */
154 "XSCALE_RX", /* 20 */
158 xscale_reg_t xscale_reg_arch_info
[] =
160 {XSCALE_MAINID
, NULL
},
161 {XSCALE_CACHETYPE
, NULL
},
163 {XSCALE_AUXCTRL
, NULL
},
169 {XSCALE_CPACCESS
, NULL
},
170 {XSCALE_IBCR0
, NULL
},
171 {XSCALE_IBCR1
, NULL
},
174 {XSCALE_DBCON
, NULL
},
175 {XSCALE_TBREG
, NULL
},
176 {XSCALE_CHKPT0
, NULL
},
177 {XSCALE_CHKPT1
, NULL
},
178 {XSCALE_DCSR
, NULL
}, /* DCSR accessed via JTAG or SW */
179 {-1, NULL
}, /* TX accessed via JTAG */
180 {-1, NULL
}, /* RX accessed via JTAG */
181 {-1, NULL
}, /* TXRXCTRL implicit access via JTAG */
184 int xscale_reg_arch_type
= -1;
186 int xscale_get_reg(reg_t
*reg
);
187 int xscale_set_reg(reg_t
*reg
, u8
*buf
);
189 int xscale_get_arch_pointers(target_t
*target
, armv4_5_common_t
**armv4_5_p
, xscale_common_t
**xscale_p
)
191 armv4_5_common_t
*armv4_5
= target
->arch_info
;
192 xscale_common_t
*xscale
= armv4_5
->arch_info
;
194 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
196 LOG_ERROR("target isn't an XScale target");
200 if (xscale
->common_magic
!= XSCALE_COMMON_MAGIC
)
202 LOG_ERROR("target isn't an XScale target");
206 *armv4_5_p
= armv4_5
;
212 int xscale_jtag_set_instr(int chain_pos
, u32 new_instr
)
214 jtag_device_t
*device
= jtag_get_device(chain_pos
);
216 if (buf_get_u32(device
->cur_instr
, 0, device
->ir_length
) != new_instr
)
220 field
.device
= chain_pos
;
221 field
.num_bits
= device
->ir_length
;
222 field
.out_value
= calloc(CEIL(field
.num_bits
, 8), 1);
223 buf_set_u32(field
.out_value
, 0, field
.num_bits
, new_instr
);
224 field
.out_mask
= NULL
;
225 field
.in_value
= NULL
;
226 jtag_set_check_value(&field
, device
->expected
, device
->expected_mask
, NULL
);
228 jtag_add_ir_scan(1, &field
, -1);
230 free(field
.out_value
);
236 int xscale_read_dcsr(target_t
*target
)
238 armv4_5_common_t
*armv4_5
= target
->arch_info
;
239 xscale_common_t
*xscale
= armv4_5
->arch_info
;
243 scan_field_t fields
[3];
245 u8 field0_check_value
= 0x2;
246 u8 field0_check_mask
= 0x7;
248 u8 field2_check_value
= 0x0;
249 u8 field2_check_mask
= 0x1;
251 jtag_add_end_state(TAP_PD
);
252 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
254 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
255 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
257 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
258 fields
[0].num_bits
= 3;
259 fields
[0].out_value
= &field0
;
260 fields
[0].out_mask
= NULL
;
261 fields
[0].in_value
= NULL
;
262 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
264 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
265 fields
[1].num_bits
= 32;
266 fields
[1].out_value
= NULL
;
267 fields
[1].out_mask
= NULL
;
268 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
269 fields
[1].in_handler
= NULL
;
270 fields
[1].in_handler_priv
= NULL
;
271 fields
[1].in_check_value
= NULL
;
272 fields
[1].in_check_mask
= NULL
;
274 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
275 fields
[2].num_bits
= 1;
276 fields
[2].out_value
= &field2
;
277 fields
[2].out_mask
= NULL
;
278 fields
[2].in_value
= NULL
;
279 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
281 jtag_add_dr_scan(3, fields
, -1);
283 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
285 LOG_ERROR("JTAG error while reading DCSR");
289 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
290 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
292 /* write the register with the value we just read
293 * on this second pass, only the first bit of field0 is guaranteed to be 0)
295 field0_check_mask
= 0x1;
296 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
297 fields
[1].in_value
= NULL
;
299 jtag_add_end_state(TAP_RTI
);
301 jtag_add_dr_scan(3, fields
, -1);
303 /* DANGER!!! this must be here. It will make sure that the arguments
304 * to jtag_set_check_value() does not go out of scope! */
305 return jtag_execute_queue();
308 int xscale_receive(target_t
*target
, u32
*buffer
, int num_words
)
311 return ERROR_INVALID_ARGUMENTS
;
314 armv4_5_common_t
*armv4_5
= target
->arch_info
;
315 xscale_common_t
*xscale
= armv4_5
->arch_info
;
317 enum tap_state path
[3];
318 scan_field_t fields
[3];
320 u8
*field0
= malloc(num_words
* 1);
321 u8 field0_check_value
= 0x2;
322 u8 field0_check_mask
= 0x6;
323 u32
*field1
= malloc(num_words
* 4);
324 u8 field2_check_value
= 0x0;
325 u8 field2_check_mask
= 0x1;
327 int words_scheduled
= 0;
335 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
336 fields
[0].num_bits
= 3;
337 fields
[0].out_value
= NULL
;
338 fields
[0].out_mask
= NULL
;
339 fields
[0].in_value
= NULL
;
340 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
342 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
343 fields
[1].num_bits
= 32;
344 fields
[1].out_value
= NULL
;
345 fields
[1].out_mask
= NULL
;
346 fields
[1].in_value
= NULL
;
347 fields
[1].in_handler
= NULL
;
348 fields
[1].in_handler_priv
= NULL
;
349 fields
[1].in_check_value
= NULL
;
350 fields
[1].in_check_mask
= NULL
;
354 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
355 fields
[2].num_bits
= 1;
356 fields
[2].out_value
= NULL
;
357 fields
[2].out_mask
= NULL
;
358 fields
[2].in_value
= NULL
;
359 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
361 jtag_add_end_state(TAP_RTI
);
362 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
363 jtag_add_runtest(1, -1); /* ensures that we're in the TAP_RTI state as the above could be a no-op */
365 /* repeat until all words have been collected */
367 while (words_done
< num_words
)
371 for (i
= words_done
; i
< num_words
; i
++)
373 fields
[0].in_value
= &field0
[i
];
374 fields
[1].in_handler
= buf_to_u32_handler
;
375 fields
[1].in_handler_priv
= (u8
*)&field1
[i
];
377 jtag_add_pathmove(3, path
);
378 jtag_add_dr_scan(3, fields
, TAP_RTI
);
382 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
384 LOG_ERROR("JTAG error while receiving data from debug handler");
388 /* examine results */
389 for (i
= words_done
; i
< num_words
; i
++)
391 if (!(field0
[0] & 1))
393 /* move backwards if necessary */
395 for (j
= i
; j
< num_words
- 1; j
++)
397 field0
[j
] = field0
[j
+1];
398 field1
[j
] = field1
[j
+1];
403 if (words_scheduled
==0)
405 if (attempts
++==1000)
407 LOG_ERROR("Failed to receiving data from debug handler after 1000 attempts");
408 retval
=ERROR_TARGET_TIMEOUT
;
413 words_done
+= words_scheduled
;
416 for (i
= 0; i
< num_words
; i
++)
417 *(buffer
++) = buf_get_u32((u8
*)&field1
[i
], 0, 32);
424 int xscale_read_tx(target_t
*target
, int consume
)
426 armv4_5_common_t
*armv4_5
= target
->arch_info
;
427 xscale_common_t
*xscale
= armv4_5
->arch_info
;
428 enum tap_state path
[3];
429 enum tap_state noconsume_path
[6];
432 struct timeval timeout
, now
;
434 scan_field_t fields
[3];
436 u8 field0_check_value
= 0x2;
437 u8 field0_check_mask
= 0x6;
438 u8 field2_check_value
= 0x0;
439 u8 field2_check_mask
= 0x1;
441 jtag_add_end_state(TAP_RTI
);
443 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
449 noconsume_path
[0] = TAP_SDS
;
450 noconsume_path
[1] = TAP_CD
;
451 noconsume_path
[2] = TAP_E1D
;
452 noconsume_path
[3] = TAP_PD
;
453 noconsume_path
[4] = TAP_E2D
;
454 noconsume_path
[5] = TAP_SD
;
456 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
457 fields
[0].num_bits
= 3;
458 fields
[0].out_value
= NULL
;
459 fields
[0].out_mask
= NULL
;
460 fields
[0].in_value
= &field0_in
;
461 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
463 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
464 fields
[1].num_bits
= 32;
465 fields
[1].out_value
= NULL
;
466 fields
[1].out_mask
= NULL
;
467 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
;
468 fields
[1].in_handler
= NULL
;
469 fields
[1].in_handler_priv
= NULL
;
470 fields
[1].in_check_value
= NULL
;
471 fields
[1].in_check_mask
= NULL
;
475 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
476 fields
[2].num_bits
= 1;
477 fields
[2].out_value
= NULL
;
478 fields
[2].out_mask
= NULL
;
479 fields
[2].in_value
= NULL
;
480 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
482 gettimeofday(&timeout
, NULL
);
483 timeval_add_time(&timeout
, 1, 0);
488 for (i
=0; i
<100; i
++)
490 /* if we want to consume the register content (i.e. clear TX_READY),
491 * we have to go straight from Capture-DR to Shift-DR
492 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
495 jtag_add_pathmove(3, path
);
498 jtag_add_pathmove(sizeof(noconsume_path
)/sizeof(*noconsume_path
), noconsume_path
);
501 jtag_add_dr_scan(3, fields
, TAP_RTI
);
503 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
505 LOG_ERROR("JTAG error while reading TX");
506 return ERROR_TARGET_TIMEOUT
;
509 gettimeofday(&now
, NULL
);
510 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
512 LOG_ERROR("time out reading TX register");
513 return ERROR_TARGET_TIMEOUT
;
515 if (!((!(field0_in
& 1)) && consume
))
520 LOG_DEBUG("waiting 10ms");
521 usleep(10*1000); /* avoid flooding the logs */
525 if (!(field0_in
& 1))
526 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
531 int xscale_write_rx(target_t
*target
)
533 armv4_5_common_t
*armv4_5
= target
->arch_info
;
534 xscale_common_t
*xscale
= armv4_5
->arch_info
;
537 struct timeval timeout
, now
;
539 scan_field_t fields
[3];
542 u8 field0_check_value
= 0x2;
543 u8 field0_check_mask
= 0x6;
545 u8 field2_check_value
= 0x0;
546 u8 field2_check_mask
= 0x1;
548 jtag_add_end_state(TAP_RTI
);
550 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
552 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
553 fields
[0].num_bits
= 3;
554 fields
[0].out_value
= &field0_out
;
555 fields
[0].out_mask
= NULL
;
556 fields
[0].in_value
= &field0_in
;
557 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
559 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
560 fields
[1].num_bits
= 32;
561 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
;
562 fields
[1].out_mask
= NULL
;
563 fields
[1].in_value
= NULL
;
564 fields
[1].in_handler
= NULL
;
565 fields
[1].in_handler_priv
= NULL
;
566 fields
[1].in_check_value
= NULL
;
567 fields
[1].in_check_mask
= NULL
;
571 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
572 fields
[2].num_bits
= 1;
573 fields
[2].out_value
= &field2
;
574 fields
[2].out_mask
= NULL
;
575 fields
[2].in_value
= NULL
;
576 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
578 gettimeofday(&timeout
, NULL
);
579 timeval_add_time(&timeout
, 1, 0);
581 /* poll until rx_read is low */
582 LOG_DEBUG("polling RX");
588 jtag_add_dr_scan(3, fields
, TAP_RTI
);
590 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
592 LOG_ERROR("JTAG error while writing RX");
596 gettimeofday(&now
, NULL
);
597 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
599 LOG_ERROR("time out writing RX register");
600 return ERROR_TARGET_TIMEOUT
;
602 if (!(field0_in
& 1))
605 LOG_DEBUG("waiting 10ms");
606 usleep(10*1000); /* wait 10ms to avoid flooding the logs */
612 jtag_add_dr_scan(3, fields
, TAP_RTI
);
614 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
616 LOG_ERROR("JTAG error while writing RX");
623 /* send count elements of size byte to the debug handler */
624 int xscale_send(target_t
*target
, u8
*buffer
, int count
, int size
)
626 armv4_5_common_t
*armv4_5
= target
->arch_info
;
627 xscale_common_t
*xscale
= armv4_5
->arch_info
;
635 jtag_add_end_state(TAP_RTI
);
637 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
644 int endianness
= target
->endianness
;
645 while (done_count
++ < count
)
650 if (endianness
== TARGET_LITTLE_ENDIAN
)
652 t
[1]=le_to_h_u32(buffer
);
655 t
[1]=be_to_h_u32(buffer
);
659 if (endianness
== TARGET_LITTLE_ENDIAN
)
661 t
[1]=le_to_h_u16(buffer
);
664 t
[1]=be_to_h_u16(buffer
);
671 LOG_ERROR("BUG: size neither 4, 2 nor 1");
674 jtag_add_dr_out(xscale
->jtag_info
.chain_pos
,
682 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
684 LOG_ERROR("JTAG error while sending data to debug handler");
691 int xscale_send_u32(target_t
*target
, u32 value
)
693 armv4_5_common_t
*armv4_5
= target
->arch_info
;
694 xscale_common_t
*xscale
= armv4_5
->arch_info
;
696 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
697 return xscale_write_rx(target
);
700 int xscale_write_dcsr(target_t
*target
, int hold_rst
, int ext_dbg_brk
)
702 armv4_5_common_t
*armv4_5
= target
->arch_info
;
703 xscale_common_t
*xscale
= armv4_5
->arch_info
;
707 scan_field_t fields
[3];
709 u8 field0_check_value
= 0x2;
710 u8 field0_check_mask
= 0x7;
712 u8 field2_check_value
= 0x0;
713 u8 field2_check_mask
= 0x1;
716 xscale
->hold_rst
= hold_rst
;
718 if (ext_dbg_brk
!= -1)
719 xscale
->external_debug_break
= ext_dbg_brk
;
721 jtag_add_end_state(TAP_RTI
);
722 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
724 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
725 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
727 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
728 fields
[0].num_bits
= 3;
729 fields
[0].out_value
= &field0
;
730 fields
[0].out_mask
= NULL
;
731 fields
[0].in_value
= NULL
;
732 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
734 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
735 fields
[1].num_bits
= 32;
736 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
737 fields
[1].out_mask
= NULL
;
738 fields
[1].in_value
= NULL
;
739 fields
[1].in_handler
= NULL
;
740 fields
[1].in_handler_priv
= NULL
;
741 fields
[1].in_check_value
= NULL
;
742 fields
[1].in_check_mask
= NULL
;
746 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
747 fields
[2].num_bits
= 1;
748 fields
[2].out_value
= &field2
;
749 fields
[2].out_mask
= NULL
;
750 fields
[2].in_value
= NULL
;
751 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
753 jtag_add_dr_scan(3, fields
, -1);
755 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
757 LOG_ERROR("JTAG error while writing DCSR");
761 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
762 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
767 /* parity of the number of bits 0 if even; 1 if odd. for 32 bit words */
768 unsigned int parity (unsigned int v
)
775 LOG_DEBUG("parity of 0x%x is %i", ov
, (0x6996 >> v
) & 1);
776 return (0x6996 >> v
) & 1;
779 int xscale_load_ic(target_t
*target
, int mini
, u32 va
, u32 buffer
[8])
781 armv4_5_common_t
*armv4_5
= target
->arch_info
;
782 xscale_common_t
*xscale
= armv4_5
->arch_info
;
787 scan_field_t fields
[2];
789 LOG_DEBUG("loading miniIC at 0x%8.8x", va
);
791 jtag_add_end_state(TAP_RTI
);
792 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
794 /* CMD is b010 for Main IC and b011 for Mini IC */
796 buf_set_u32(&cmd
, 0, 3, 0x3);
798 buf_set_u32(&cmd
, 0, 3, 0x2);
800 buf_set_u32(&cmd
, 3, 3, 0x0);
802 /* virtual address of desired cache line */
803 buf_set_u32(packet
, 0, 27, va
>> 5);
805 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
806 fields
[0].num_bits
= 6;
807 fields
[0].out_value
= &cmd
;
808 fields
[0].out_mask
= NULL
;
809 fields
[0].in_value
= NULL
;
810 fields
[0].in_check_value
= NULL
;
811 fields
[0].in_check_mask
= NULL
;
812 fields
[0].in_handler
= NULL
;
813 fields
[0].in_handler_priv
= NULL
;
815 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
816 fields
[1].num_bits
= 27;
817 fields
[1].out_value
= packet
;
818 fields
[1].out_mask
= NULL
;
819 fields
[1].in_value
= NULL
;
820 fields
[1].in_check_value
= NULL
;
821 fields
[1].in_check_mask
= NULL
;
822 fields
[1].in_handler
= NULL
;
823 fields
[1].in_handler_priv
= NULL
;
825 jtag_add_dr_scan(2, fields
, -1);
827 fields
[0].num_bits
= 32;
828 fields
[0].out_value
= packet
;
830 fields
[1].num_bits
= 1;
831 fields
[1].out_value
= &cmd
;
833 for (word
= 0; word
< 8; word
++)
835 buf_set_u32(packet
, 0, 32, buffer
[word
]);
836 cmd
= parity(*((u32
*)packet
));
837 jtag_add_dr_scan(2, fields
, -1);
840 jtag_execute_queue();
845 int xscale_invalidate_ic_line(target_t
*target
, u32 va
)
847 armv4_5_common_t
*armv4_5
= target
->arch_info
;
848 xscale_common_t
*xscale
= armv4_5
->arch_info
;
852 scan_field_t fields
[2];
854 jtag_add_end_state(TAP_RTI
);
855 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
857 /* CMD for invalidate IC line b000, bits [6:4] b000 */
858 buf_set_u32(&cmd
, 0, 6, 0x0);
860 /* virtual address of desired cache line */
861 buf_set_u32(packet
, 0, 27, va
>> 5);
863 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
864 fields
[0].num_bits
= 6;
865 fields
[0].out_value
= &cmd
;
866 fields
[0].out_mask
= NULL
;
867 fields
[0].in_value
= NULL
;
868 fields
[0].in_check_value
= NULL
;
869 fields
[0].in_check_mask
= NULL
;
870 fields
[0].in_handler
= NULL
;
871 fields
[0].in_handler_priv
= NULL
;
873 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
874 fields
[1].num_bits
= 27;
875 fields
[1].out_value
= packet
;
876 fields
[1].out_mask
= NULL
;
877 fields
[1].in_value
= NULL
;
878 fields
[1].in_check_value
= NULL
;
879 fields
[1].in_check_mask
= NULL
;
880 fields
[1].in_handler
= NULL
;
881 fields
[1].in_handler_priv
= NULL
;
883 jtag_add_dr_scan(2, fields
, -1);
888 int xscale_update_vectors(target_t
*target
)
890 armv4_5_common_t
*armv4_5
= target
->arch_info
;
891 xscale_common_t
*xscale
= armv4_5
->arch_info
;
895 u32 low_reset_branch
, high_reset_branch
;
897 for (i
= 1; i
< 8; i
++)
899 /* if there's a static vector specified for this exception, override */
900 if (xscale
->static_high_vectors_set
& (1 << i
))
902 xscale
->high_vectors
[i
] = xscale
->static_high_vectors
[i
];
906 retval
=target_read_u32(target
, 0xffff0000 + 4*i
, &xscale
->high_vectors
[i
]);
907 if (retval
== ERROR_TARGET_TIMEOUT
)
909 if (retval
!=ERROR_OK
)
911 /* Some of these reads will fail as part of normal execution */
912 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
917 for (i
= 1; i
< 8; i
++)
919 if (xscale
->static_low_vectors_set
& (1 << i
))
921 xscale
->low_vectors
[i
] = xscale
->static_low_vectors
[i
];
925 retval
=target_read_u32(target
, 0x0 + 4*i
, &xscale
->low_vectors
[i
]);
926 if (retval
== ERROR_TARGET_TIMEOUT
)
928 if (retval
!=ERROR_OK
)
930 /* Some of these reads will fail as part of normal execution */
931 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
936 /* calculate branches to debug handler */
937 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
938 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
940 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
941 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
943 /* invalidate and load exception vectors in mini i-cache */
944 xscale_invalidate_ic_line(target
, 0x0);
945 xscale_invalidate_ic_line(target
, 0xffff0000);
947 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
948 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
953 int xscale_arch_state(struct target_s
*target
)
955 armv4_5_common_t
*armv4_5
= target
->arch_info
;
956 xscale_common_t
*xscale
= armv4_5
->arch_info
;
960 "disabled", "enabled"
963 char *arch_dbg_reason
[] =
965 "", "\n(processor reset)", "\n(trace buffer full)"
968 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
970 LOG_ERROR("BUG: called for a non-ARMv4/5 target");
974 LOG_USER("target halted in %s state due to %s, current mode: %s\n"
975 "cpsr: 0x%8.8x pc: 0x%8.8x\n"
976 "MMU: %s, D-Cache: %s, I-Cache: %s"
978 armv4_5_state_strings
[armv4_5
->core_state
],
979 target_debug_reason_strings
[target
->debug_reason
],
980 armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)],
981 buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32),
982 buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32),
983 state
[xscale
->armv4_5_mmu
.mmu_enabled
],
984 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
],
985 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
],
986 arch_dbg_reason
[xscale
->arch_debug_reason
]);
991 int xscale_poll(target_t
*target
)
994 armv4_5_common_t
*armv4_5
= target
->arch_info
;
995 xscale_common_t
*xscale
= armv4_5
->arch_info
;
997 if ((target
->state
== TARGET_RUNNING
) || (target
->state
== TARGET_DEBUG_RUNNING
))
999 enum target_state previous_state
= target
->state
;
1000 if ((retval
= xscale_read_tx(target
, 0)) == ERROR_OK
)
1003 /* there's data to read from the tx register, we entered debug state */
1004 xscale
->handler_running
= 1;
1006 target
->state
= TARGET_HALTED
;
1008 /* process debug entry, fetching current mode regs */
1009 retval
= xscale_debug_entry(target
);
1011 else if (retval
!= ERROR_TARGET_RESOURCE_NOT_AVAILABLE
)
1013 LOG_USER("error while polling TX register, reset CPU");
1014 /* here we "lie" so GDB won't get stuck and a reset can be perfomed */
1015 target
->state
= TARGET_HALTED
;
1018 /* debug_entry could have overwritten target state (i.e. immediate resume)
1019 * don't signal event handlers in that case
1021 if (target
->state
!= TARGET_HALTED
)
1024 /* if target was running, signal that we halted
1025 * otherwise we reentered from debug execution */
1026 if (previous_state
== TARGET_RUNNING
)
1027 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1029 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_HALTED
);
1035 int xscale_debug_entry(target_t
*target
)
1037 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1038 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1046 /* clear external dbg break (will be written on next DCSR read) */
1047 xscale
->external_debug_break
= 0;
1048 if ((retval
=xscale_read_dcsr(target
))!=ERROR_OK
)
1051 /* get r0, pc, r1 to r7 and cpsr */
1052 if ((retval
=xscale_receive(target
, buffer
, 10))!=ERROR_OK
)
1055 /* move r0 from buffer to register cache */
1056 buf_set_u32(armv4_5
->core_cache
->reg_list
[0].value
, 0, 32, buffer
[0]);
1057 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1058 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1059 LOG_DEBUG("r0: 0x%8.8x", buffer
[0]);
1061 /* move pc from buffer to register cache */
1062 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, buffer
[1]);
1063 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1064 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1065 LOG_DEBUG("pc: 0x%8.8x", buffer
[1]);
1067 /* move data from buffer to register cache */
1068 for (i
= 1; i
<= 7; i
++)
1070 buf_set_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32, buffer
[1 + i
]);
1071 armv4_5
->core_cache
->reg_list
[i
].dirty
= 1;
1072 armv4_5
->core_cache
->reg_list
[i
].valid
= 1;
1073 LOG_DEBUG("r%i: 0x%8.8x", i
, buffer
[i
+ 1]);
1076 buf_set_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32, buffer
[9]);
1077 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].dirty
= 1;
1078 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].valid
= 1;
1079 LOG_DEBUG("cpsr: 0x%8.8x", buffer
[9]);
1081 armv4_5
->core_mode
= buffer
[9] & 0x1f;
1082 if (armv4_5_mode_to_number(armv4_5
->core_mode
) == -1)
1084 target
->state
= TARGET_UNKNOWN
;
1085 LOG_ERROR("cpsr contains invalid mode value - communication failure");
1086 return ERROR_TARGET_FAILURE
;
1088 LOG_DEBUG("target entered debug state in %s mode", armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)]);
1090 if (buffer
[9] & 0x20)
1091 armv4_5
->core_state
= ARMV4_5_STATE_THUMB
;
1093 armv4_5
->core_state
= ARMV4_5_STATE_ARM
;
1096 if (armv4_5_mode_to_number(armv4_5
->core_mode
)==-1)
1099 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1100 if ((armv4_5
->core_mode
!= ARMV4_5_MODE_USR
) && (armv4_5
->core_mode
!= ARMV4_5_MODE_SYS
))
1102 xscale_receive(target
, buffer
, 8);
1103 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1104 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).dirty
= 0;
1105 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).valid
= 1;
1109 /* r8 to r14, but no spsr */
1110 xscale_receive(target
, buffer
, 7);
1113 /* move data from buffer to register cache */
1114 for (i
= 8; i
<= 14; i
++)
1116 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).value
, 0, 32, buffer
[i
- 8]);
1117 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).dirty
= 0;
1118 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).valid
= 1;
1121 /* examine debug reason */
1122 xscale_read_dcsr(target
);
1123 moe
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 2, 3);
1125 /* stored PC (for calculating fixup) */
1126 pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1130 case 0x0: /* Processor reset */
1131 target
->debug_reason
= DBG_REASON_DBGRQ
;
1132 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_RESET
;
1135 case 0x1: /* Instruction breakpoint hit */
1136 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1137 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1140 case 0x2: /* Data breakpoint hit */
1141 target
->debug_reason
= DBG_REASON_WATCHPOINT
;
1142 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1145 case 0x3: /* BKPT instruction executed */
1146 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1147 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1150 case 0x4: /* Ext. debug event */
1151 target
->debug_reason
= DBG_REASON_DBGRQ
;
1152 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1155 case 0x5: /* Vector trap occured */
1156 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1157 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1160 case 0x6: /* Trace buffer full break */
1161 target
->debug_reason
= DBG_REASON_DBGRQ
;
1162 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_TB_FULL
;
1165 case 0x7: /* Reserved */
1167 LOG_ERROR("Method of Entry is 'Reserved'");
1172 /* apply PC fixup */
1173 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, pc
);
1175 /* on the first debug entry, identify cache type */
1176 if (xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
== -1)
1180 /* read cp15 cache type register */
1181 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
]);
1182 cache_type_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
].value
, 0, 32);
1184 armv4_5_identify_cache(cache_type_reg
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
1187 /* examine MMU and Cache settings */
1188 /* read cp15 control register */
1189 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
1190 xscale
->cp15_control_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
1191 xscale
->armv4_5_mmu
.mmu_enabled
= (xscale
->cp15_control_reg
& 0x1U
) ? 1 : 0;
1192 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= (xscale
->cp15_control_reg
& 0x4U
) ? 1 : 0;
1193 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= (xscale
->cp15_control_reg
& 0x1000U
) ? 1 : 0;
1195 /* tracing enabled, read collected trace data */
1196 if (xscale
->trace
.buffer_enabled
)
1198 xscale_read_trace(target
);
1199 xscale
->trace
.buffer_fill
--;
1201 /* resume if we're still collecting trace data */
1202 if ((xscale
->arch_debug_reason
== XSCALE_DBG_REASON_TB_FULL
)
1203 && (xscale
->trace
.buffer_fill
> 0))
1205 xscale_resume(target
, 1, 0x0, 1, 0);
1209 xscale
->trace
.buffer_enabled
= 0;
1216 int xscale_halt(target_t
*target
)
1218 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1219 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1221 LOG_DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1223 if (target
->state
== TARGET_HALTED
)
1225 LOG_DEBUG("target was already halted");
1228 else if (target
->state
== TARGET_UNKNOWN
)
1230 /* this must not happen for a xscale target */
1231 LOG_ERROR("target was in unknown state when halt was requested");
1232 return ERROR_TARGET_INVALID
;
1234 else if (target
->state
== TARGET_RESET
)
1236 LOG_DEBUG("target->state == TARGET_RESET");
1240 /* assert external dbg break */
1241 xscale
->external_debug_break
= 1;
1242 xscale_read_dcsr(target
);
1244 target
->debug_reason
= DBG_REASON_DBGRQ
;
1250 int xscale_enable_single_step(struct target_s
*target
, u32 next_pc
)
1252 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1253 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1254 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1256 if (xscale
->ibcr0_used
)
1258 breakpoint_t
*ibcr0_bp
= breakpoint_find(target
, buf_get_u32(ibcr0
->value
, 0, 32) & 0xfffffffe);
1262 xscale_unset_breakpoint(target
, ibcr0_bp
);
1266 LOG_ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1271 xscale_set_reg_u32(ibcr0
, next_pc
| 0x1);
1276 int xscale_disable_single_step(struct target_s
*target
)
1278 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1279 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1280 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1282 xscale_set_reg_u32(ibcr0
, 0x0);
1287 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
)
1289 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1290 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1291 breakpoint_t
*breakpoint
= target
->breakpoints
;
1300 if (target
->state
!= TARGET_HALTED
)
1302 LOG_WARNING("target not halted");
1303 return ERROR_TARGET_NOT_HALTED
;
1306 if (!debug_execution
)
1308 target_free_all_working_areas(target
);
1311 /* update vector tables */
1312 if ((retval
=xscale_update_vectors(target
))!=ERROR_OK
)
1315 /* current = 1: continue on current pc, otherwise continue at <address> */
1317 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1319 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1321 /* if we're at the reset vector, we have to simulate the branch */
1322 if (current_pc
== 0x0)
1324 arm_simulate_step(target
, NULL
);
1325 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1328 /* the front-end may request us not to handle breakpoints */
1329 if (handle_breakpoints
)
1331 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1335 /* there's a breakpoint at the current PC, we have to step over it */
1336 LOG_DEBUG("unset breakpoint at 0x%8.8x", breakpoint
->address
);
1337 xscale_unset_breakpoint(target
, breakpoint
);
1339 /* calculate PC of next instruction */
1340 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1343 target_read_u32(target
, current_pc
, ¤t_opcode
);
1344 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1347 LOG_DEBUG("enable single-step");
1348 xscale_enable_single_step(target
, next_pc
);
1350 /* restore banked registers */
1351 xscale_restore_context(target
);
1353 /* send resume request (command 0x30 or 0x31)
1354 * clean the trace buffer if it is to be enabled (0x62) */
1355 if (xscale
->trace
.buffer_enabled
)
1357 xscale_send_u32(target
, 0x62);
1358 xscale_send_u32(target
, 0x31);
1361 xscale_send_u32(target
, 0x30);
1364 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1365 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1367 for (i
= 7; i
>= 0; i
--)
1370 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1371 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1375 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1376 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1378 /* wait for and process debug entry */
1379 xscale_debug_entry(target
);
1381 LOG_DEBUG("disable single-step");
1382 xscale_disable_single_step(target
);
1384 LOG_DEBUG("set breakpoint at 0x%8.8x", breakpoint
->address
);
1385 xscale_set_breakpoint(target
, breakpoint
);
1389 /* enable any pending breakpoints and watchpoints */
1390 xscale_enable_breakpoints(target
);
1391 xscale_enable_watchpoints(target
);
1393 /* restore banked registers */
1394 xscale_restore_context(target
);
1396 /* send resume request (command 0x30 or 0x31)
1397 * clean the trace buffer if it is to be enabled (0x62) */
1398 if (xscale
->trace
.buffer_enabled
)
1400 xscale_send_u32(target
, 0x62);
1401 xscale_send_u32(target
, 0x31);
1404 xscale_send_u32(target
, 0x30);
1407 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1408 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1410 for (i
= 7; i
>= 0; i
--)
1413 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1414 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1418 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1419 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1421 target
->debug_reason
= DBG_REASON_NOTHALTED
;
1423 if (!debug_execution
)
1425 /* registers are now invalid */
1426 armv4_5_invalidate_core_regs(target
);
1427 target
->state
= TARGET_RUNNING
;
1428 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1432 target
->state
= TARGET_DEBUG_RUNNING
;
1433 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1436 LOG_DEBUG("target resumed");
1438 xscale
->handler_running
= 1;
1443 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
)
1445 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1446 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1447 breakpoint_t
*breakpoint
= target
->breakpoints
;
1449 u32 current_pc
, next_pc
;
1453 if (target
->state
!= TARGET_HALTED
)
1455 LOG_WARNING("target not halted");
1456 return ERROR_TARGET_NOT_HALTED
;
1459 /* current = 1: continue on current pc, otherwise continue at <address> */
1461 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1463 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1465 /* if we're at the reset vector, we have to simulate the step */
1466 if (current_pc
== 0x0)
1468 arm_simulate_step(target
, NULL
);
1469 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1471 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1472 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1477 /* the front-end may request us not to handle breakpoints */
1478 if (handle_breakpoints
)
1479 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1481 xscale_unset_breakpoint(target
, breakpoint
);
1484 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1486 /* calculate PC of next instruction */
1487 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1490 target_read_u32(target
, current_pc
, ¤t_opcode
);
1491 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1494 LOG_DEBUG("enable single-step");
1495 xscale_enable_single_step(target
, next_pc
);
1497 /* restore banked registers */
1498 xscale_restore_context(target
);
1500 /* send resume request (command 0x30 or 0x31)
1501 * clean the trace buffer if it is to be enabled (0x62) */
1502 if (xscale
->trace
.buffer_enabled
)
1504 xscale_send_u32(target
, 0x62);
1505 xscale_send_u32(target
, 0x31);
1508 xscale_send_u32(target
, 0x30);
1511 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1512 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1514 for (i
= 7; i
>= 0; i
--)
1517 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1518 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1522 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1523 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1525 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1527 /* registers are now invalid */
1528 armv4_5_invalidate_core_regs(target
);
1530 /* wait for and process debug entry */
1531 xscale_debug_entry(target
);
1533 LOG_DEBUG("disable single-step");
1534 xscale_disable_single_step(target
);
1536 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1540 xscale_set_breakpoint(target
, breakpoint
);
1543 LOG_DEBUG("target stepped");
1549 int xscale_assert_reset(target_t
*target
)
1551 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1552 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1554 LOG_DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1556 /* select DCSR instruction (set endstate to R-T-I to ensure we don't
1557 * end up in T-L-R, which would reset JTAG
1559 jtag_add_end_state(TAP_RTI
);
1560 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
1562 /* set Hold reset, Halt mode and Trap Reset */
1563 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1564 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1565 xscale_write_dcsr(target
, 1, 0);
1567 /* select BYPASS, because having DCSR selected caused problems on the PXA27x */
1568 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, 0x7f);
1569 jtag_execute_queue();
1572 jtag_add_reset(0, 1);
1574 /* sleep 1ms, to be sure we fulfill any requirements */
1575 jtag_add_sleep(1000);
1576 jtag_execute_queue();
1578 target
->state
= TARGET_RESET
;
1583 int xscale_deassert_reset(target_t
*target
)
1585 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1586 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1588 fileio_t debug_handler
;
1596 breakpoint_t
*breakpoint
= target
->breakpoints
;
1600 xscale
->ibcr_available
= 2;
1601 xscale
->ibcr0_used
= 0;
1602 xscale
->ibcr1_used
= 0;
1604 xscale
->dbr_available
= 2;
1605 xscale
->dbr0_used
= 0;
1606 xscale
->dbr1_used
= 0;
1608 /* mark all hardware breakpoints as unset */
1611 if (breakpoint
->type
== BKPT_HARD
)
1613 breakpoint
->set
= 0;
1615 breakpoint
= breakpoint
->next
;
1618 if (!xscale
->handler_installed
)
1621 jtag_add_reset(0, 0);
1623 /* wait 300ms; 150 and 100ms were not enough */
1624 jtag_add_sleep(300*1000);
1626 jtag_add_runtest(2030, TAP_RTI
);
1627 jtag_execute_queue();
1629 /* set Hold reset, Halt mode and Trap Reset */
1630 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1631 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1632 xscale_write_dcsr(target
, 1, 0);
1634 /* Load debug handler */
1635 if (fileio_open(&debug_handler
, "xscale/debug_handler.bin", FILEIO_READ
, FILEIO_BINARY
) != ERROR_OK
)
1640 if ((binary_size
= debug_handler
.size
) % 4)
1642 LOG_ERROR("debug_handler.bin: size not a multiple of 4");
1646 if (binary_size
> 0x800)
1648 LOG_ERROR("debug_handler.bin: larger than 2kb");
1652 binary_size
= CEIL(binary_size
, 32) * 32;
1654 address
= xscale
->handler_address
;
1655 while (binary_size
> 0)
1660 if ((retval
= fileio_read(&debug_handler
, 32, buffer
, &buf_cnt
)) != ERROR_OK
)
1665 for (i
= 0; i
< buf_cnt
; i
+= 4)
1667 /* convert LE buffer to host-endian u32 */
1668 cache_line
[i
/ 4] = le_to_h_u32(&buffer
[i
]);
1671 for (; buf_cnt
< 32; buf_cnt
+= 4)
1673 cache_line
[buf_cnt
/ 4] = 0xe1a08008;
1676 /* only load addresses other than the reset vectors */
1677 if ((address
% 0x400) != 0x0)
1679 xscale_load_ic(target
, 1, address
, cache_line
);
1683 binary_size
-= buf_cnt
;
1686 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
1687 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
1689 jtag_add_runtest(30, TAP_RTI
);
1691 jtag_add_sleep(100000);
1693 /* set Hold reset, Halt mode and Trap Reset */
1694 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1695 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1696 xscale_write_dcsr(target
, 1, 0);
1698 /* clear Hold reset to let the target run (should enter debug handler) */
1699 xscale_write_dcsr(target
, 0, 1);
1700 target
->state
= TARGET_RUNNING
;
1702 if ((target
->reset_mode
!= RESET_HALT
) && (target
->reset_mode
!= RESET_INIT
))
1704 jtag_add_sleep(10000);
1706 /* we should have entered debug now */
1707 xscale_debug_entry(target
);
1708 target
->state
= TARGET_HALTED
;
1710 /* resume the target */
1711 xscale_resume(target
, 1, 0x0, 1, 0);
1714 fileio_close(&debug_handler
);
1718 jtag_add_reset(0, 0);
1725 int xscale_soft_reset_halt(struct target_s
*target
)
1731 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
)
1737 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
)
1743 int xscale_full_context(target_t
*target
)
1745 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1753 if (target
->state
!= TARGET_HALTED
)
1755 LOG_WARNING("target not halted");
1756 return ERROR_TARGET_NOT_HALTED
;
1759 buffer
= malloc(4 * 8);
1761 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1762 * we can't enter User mode on an XScale (unpredictable),
1763 * but User shares registers with SYS
1765 for(i
= 1; i
< 7; i
++)
1769 /* check if there are invalid registers in the current mode
1771 for (j
= 0; j
<= 16; j
++)
1773 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
== 0)
1781 /* request banked registers */
1782 xscale_send_u32(target
, 0x0);
1785 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1786 tmp_cpsr
|= 0xc0; /* I/F bits */
1788 /* send CPSR for desired mode */
1789 xscale_send_u32(target
, tmp_cpsr
);
1791 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1792 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1794 xscale_receive(target
, buffer
, 8);
1795 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1796 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1797 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).valid
= 1;
1801 xscale_receive(target
, buffer
, 7);
1804 /* move data from buffer to register cache */
1805 for (j
= 8; j
<= 14; j
++)
1807 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]);
1808 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1809 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
= 1;
1819 int xscale_restore_context(target_t
*target
)
1821 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1827 if (target
->state
!= TARGET_HALTED
)
1829 LOG_WARNING("target not halted");
1830 return ERROR_TARGET_NOT_HALTED
;
1833 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1834 * we can't enter User mode on an XScale (unpredictable),
1835 * but User shares registers with SYS
1837 for(i
= 1; i
< 7; i
++)
1841 /* check if there are invalid registers in the current mode
1843 for (j
= 8; j
<= 14; j
++)
1845 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
== 1)
1849 /* if not USR/SYS, check if the SPSR needs to be written */
1850 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1852 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
== 1)
1860 /* send banked registers */
1861 xscale_send_u32(target
, 0x1);
1864 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1865 tmp_cpsr
|= 0xc0; /* I/F bits */
1867 /* send CPSR for desired mode */
1868 xscale_send_u32(target
, tmp_cpsr
);
1870 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1871 for (j
= 8; j
<= 14; j
++)
1873 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, j
).value
, 0, 32));
1874 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1877 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1879 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32));
1880 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1888 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1890 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1891 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1896 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1898 if (target
->state
!= TARGET_HALTED
)
1900 LOG_WARNING("target not halted");
1901 return ERROR_TARGET_NOT_HALTED
;
1904 /* sanitize arguments */
1905 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1906 return ERROR_INVALID_ARGUMENTS
;
1908 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1909 return ERROR_TARGET_UNALIGNED_ACCESS
;
1911 /* send memory read request (command 0x1n, n: access size) */
1912 if ((retval
=xscale_send_u32(target
, 0x10 | size
))!=ERROR_OK
)
1915 /* send base address for read request */
1916 if ((retval
=xscale_send_u32(target
, address
))!=ERROR_OK
)
1919 /* send number of requested data words */
1920 if ((retval
=xscale_send_u32(target
, count
))!=ERROR_OK
)
1923 /* receive data from target (count times 32-bit words in host endianness) */
1924 buf32
= malloc(4 * count
);
1925 if ((retval
=xscale_receive(target
, buf32
, count
))!=ERROR_OK
)
1928 /* extract data from host-endian buffer into byte stream */
1929 for (i
= 0; i
< count
; i
++)
1934 target_buffer_set_u32(target
, buffer
, buf32
[i
]);
1938 target_buffer_set_u16(target
, buffer
, buf32
[i
] & 0xffff);
1942 *buffer
++ = buf32
[i
] & 0xff;
1945 LOG_ERROR("should never get here");
1952 /* examine DCSR, to see if Sticky Abort (SA) got set */
1953 if ((retval
=xscale_read_dcsr(target
))!=ERROR_OK
)
1955 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1958 if ((retval
=xscale_send_u32(target
, 0x60))!=ERROR_OK
)
1961 return ERROR_TARGET_DATA_ABORT
;
1967 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1969 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1970 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1973 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1975 if (target
->state
!= TARGET_HALTED
)
1977 LOG_WARNING("target not halted");
1978 return ERROR_TARGET_NOT_HALTED
;
1981 /* sanitize arguments */
1982 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1983 return ERROR_INVALID_ARGUMENTS
;
1985 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1986 return ERROR_TARGET_UNALIGNED_ACCESS
;
1988 /* send memory write request (command 0x2n, n: access size) */
1989 if ((retval
=xscale_send_u32(target
, 0x20 | size
))!=ERROR_OK
)
1992 /* send base address for read request */
1993 if ((retval
=xscale_send_u32(target
, address
))!=ERROR_OK
)
1996 /* send number of requested data words to be written*/
1997 if ((retval
=xscale_send_u32(target
, count
))!=ERROR_OK
)
2000 /* extract data from host-endian buffer into byte stream */
2002 for (i
= 0; i
< count
; i
++)
2007 value
= target_buffer_get_u32(target
, buffer
);
2008 xscale_send_u32(target
, value
);
2012 value
= target_buffer_get_u16(target
, buffer
);
2013 xscale_send_u32(target
, value
);
2018 xscale_send_u32(target
, value
);
2022 LOG_ERROR("should never get here");
2027 if ((retval
=xscale_send(target
, buffer
, count
, size
))!=ERROR_OK
)
2030 /* examine DCSR, to see if Sticky Abort (SA) got set */
2031 if ((retval
=xscale_read_dcsr(target
))!=ERROR_OK
)
2033 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
2036 if ((retval
=xscale_send_u32(target
, 0x60))!=ERROR_OK
)
2039 return ERROR_TARGET_DATA_ABORT
;
2045 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
)
2047 return xscale_write_memory(target
, address
, 4, count
, buffer
);
2050 int xscale_checksum_memory(struct target_s
*target
, u32 address
, u32 count
, u32
* checksum
)
2052 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2055 u32
xscale_get_ttb(target_t
*target
)
2057 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2058 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2061 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_TTB
]);
2062 ttb
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_TTB
].value
, 0, 32);
2067 void xscale_disable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2069 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2070 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2073 /* read cp15 control register */
2074 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2075 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2078 cp15_control
&= ~0x1U
;
2083 xscale_send_u32(target
, 0x50);
2084 xscale_send_u32(target
, xscale
->cache_clean_address
);
2086 /* invalidate DCache */
2087 xscale_send_u32(target
, 0x51);
2089 cp15_control
&= ~0x4U
;
2094 /* invalidate ICache */
2095 xscale_send_u32(target
, 0x52);
2096 cp15_control
&= ~0x1000U
;
2099 /* write new cp15 control register */
2100 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2102 /* execute cpwait to ensure outstanding operations complete */
2103 xscale_send_u32(target
, 0x53);
2106 void xscale_enable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2108 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2109 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2112 /* read cp15 control register */
2113 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2114 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2117 cp15_control
|= 0x1U
;
2120 cp15_control
|= 0x4U
;
2123 cp15_control
|= 0x1000U
;
2125 /* write new cp15 control register */
2126 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2128 /* execute cpwait to ensure outstanding operations complete */
2129 xscale_send_u32(target
, 0x53);
2132 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2134 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2135 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2137 if (target
->state
!= TARGET_HALTED
)
2139 LOG_WARNING("target not halted");
2140 return ERROR_TARGET_NOT_HALTED
;
2143 if (xscale
->force_hw_bkpts
)
2144 breakpoint
->type
= BKPT_HARD
;
2146 if (breakpoint
->set
)
2148 LOG_WARNING("breakpoint already set");
2152 if (breakpoint
->type
== BKPT_HARD
)
2154 u32 value
= breakpoint
->address
| 1;
2155 if (!xscale
->ibcr0_used
)
2157 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], value
);
2158 xscale
->ibcr0_used
= 1;
2159 breakpoint
->set
= 1; /* breakpoint set on first breakpoint register */
2161 else if (!xscale
->ibcr1_used
)
2163 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], value
);
2164 xscale
->ibcr1_used
= 1;
2165 breakpoint
->set
= 2; /* breakpoint set on second breakpoint register */
2169 LOG_ERROR("BUG: no hardware comparator available");
2173 else if (breakpoint
->type
== BKPT_SOFT
)
2175 if (breakpoint
->length
== 4)
2177 /* keep the original instruction in target endianness */
2178 target
->type
->read_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2179 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2180 target_write_u32(target
, breakpoint
->address
, xscale
->arm_bkpt
);
2184 /* keep the original instruction in target endianness */
2185 target
->type
->read_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2186 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2187 target_write_u32(target
, breakpoint
->address
, xscale
->thumb_bkpt
);
2189 breakpoint
->set
= 1;
2196 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2198 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2199 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2201 if (target
->state
!= TARGET_HALTED
)
2203 LOG_WARNING("target not halted");
2204 return ERROR_TARGET_NOT_HALTED
;
2207 if (xscale
->force_hw_bkpts
)
2209 LOG_DEBUG("forcing use of hardware breakpoint at address 0x%8.8x", breakpoint
->address
);
2210 breakpoint
->type
= BKPT_HARD
;
2213 if ((breakpoint
->type
== BKPT_HARD
) && (xscale
->ibcr_available
< 1))
2215 LOG_INFO("no breakpoint unit available for hardware breakpoint");
2216 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2220 xscale
->ibcr_available
--;
2223 if ((breakpoint
->length
!= 2) && (breakpoint
->length
!= 4))
2225 LOG_INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2226 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2232 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2234 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2235 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2237 if (target
->state
!= TARGET_HALTED
)
2239 LOG_WARNING("target not halted");
2240 return ERROR_TARGET_NOT_HALTED
;
2243 if (!breakpoint
->set
)
2245 LOG_WARNING("breakpoint not set");
2249 if (breakpoint
->type
== BKPT_HARD
)
2251 if (breakpoint
->set
== 1)
2253 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], 0x0);
2254 xscale
->ibcr0_used
= 0;
2256 else if (breakpoint
->set
== 2)
2258 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], 0x0);
2259 xscale
->ibcr1_used
= 0;
2261 breakpoint
->set
= 0;
2265 /* restore original instruction (kept in target endianness) */
2266 if (breakpoint
->length
== 4)
2268 target
->type
->write_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2272 target
->type
->write_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2274 breakpoint
->set
= 0;
2280 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2282 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2283 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2285 if (target
->state
!= TARGET_HALTED
)
2287 LOG_WARNING("target not halted");
2288 return ERROR_TARGET_NOT_HALTED
;
2291 if (breakpoint
->set
)
2293 xscale_unset_breakpoint(target
, breakpoint
);
2296 if (breakpoint
->type
== BKPT_HARD
)
2297 xscale
->ibcr_available
++;
2302 int xscale_set_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2304 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2305 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2307 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2308 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2310 if (target
->state
!= TARGET_HALTED
)
2312 LOG_WARNING("target not halted");
2313 return ERROR_TARGET_NOT_HALTED
;
2316 xscale_get_reg(dbcon
);
2318 switch (watchpoint
->rw
)
2330 LOG_ERROR("BUG: watchpoint->rw neither read, write nor access");
2333 if (!xscale
->dbr0_used
)
2335 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR0
], watchpoint
->address
);
2336 dbcon_value
|= enable
;
2337 xscale_set_reg_u32(dbcon
, dbcon_value
);
2338 watchpoint
->set
= 1;
2339 xscale
->dbr0_used
= 1;
2341 else if (!xscale
->dbr1_used
)
2343 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR1
], watchpoint
->address
);
2344 dbcon_value
|= enable
<< 2;
2345 xscale_set_reg_u32(dbcon
, dbcon_value
);
2346 watchpoint
->set
= 2;
2347 xscale
->dbr1_used
= 1;
2351 LOG_ERROR("BUG: no hardware comparator available");
2358 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2360 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2361 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2363 if (target
->state
!= TARGET_HALTED
)
2365 LOG_WARNING("target not halted");
2366 return ERROR_TARGET_NOT_HALTED
;
2369 if (xscale
->dbr_available
< 1)
2371 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2374 if ((watchpoint
->length
!= 1) && (watchpoint
->length
!= 2) && (watchpoint
->length
!= 4))
2376 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2379 xscale
->dbr_available
--;
2384 int xscale_unset_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2386 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2387 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2388 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2389 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2391 if (target
->state
!= TARGET_HALTED
)
2393 LOG_WARNING("target not halted");
2394 return ERROR_TARGET_NOT_HALTED
;
2397 if (!watchpoint
->set
)
2399 LOG_WARNING("breakpoint not set");
2403 if (watchpoint
->set
== 1)
2405 dbcon_value
&= ~0x3;
2406 xscale_set_reg_u32(dbcon
, dbcon_value
);
2407 xscale
->dbr0_used
= 0;
2409 else if (watchpoint
->set
== 2)
2411 dbcon_value
&= ~0xc;
2412 xscale_set_reg_u32(dbcon
, dbcon_value
);
2413 xscale
->dbr1_used
= 0;
2415 watchpoint
->set
= 0;
2420 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2422 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2423 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2425 if (target
->state
!= TARGET_HALTED
)
2427 LOG_WARNING("target not halted");
2428 return ERROR_TARGET_NOT_HALTED
;
2431 if (watchpoint
->set
)
2433 xscale_unset_watchpoint(target
, watchpoint
);
2436 xscale
->dbr_available
++;
2441 void xscale_enable_watchpoints(struct target_s
*target
)
2443 watchpoint_t
*watchpoint
= target
->watchpoints
;
2447 if (watchpoint
->set
== 0)
2448 xscale_set_watchpoint(target
, watchpoint
);
2449 watchpoint
= watchpoint
->next
;
2453 void xscale_enable_breakpoints(struct target_s
*target
)
2455 breakpoint_t
*breakpoint
= target
->breakpoints
;
2457 /* set any pending breakpoints */
2460 if (breakpoint
->set
== 0)
2461 xscale_set_breakpoint(target
, breakpoint
);
2462 breakpoint
= breakpoint
->next
;
2466 int xscale_get_reg(reg_t
*reg
)
2468 xscale_reg_t
*arch_info
= reg
->arch_info
;
2469 target_t
*target
= arch_info
->target
;
2470 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2471 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2473 /* DCSR, TX and RX are accessible via JTAG */
2474 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2476 return xscale_read_dcsr(arch_info
->target
);
2478 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2480 /* 1 = consume register content */
2481 return xscale_read_tx(arch_info
->target
, 1);
2483 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2485 /* can't read from RX register (host -> debug handler) */
2488 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2490 /* can't (explicitly) read from TXRXCTRL register */
2493 else /* Other DBG registers have to be transfered by the debug handler */
2495 /* send CP read request (command 0x40) */
2496 xscale_send_u32(target
, 0x40);
2498 /* send CP register number */
2499 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2501 /* read register value */
2502 xscale_read_tx(target
, 1);
2503 buf_cpy(xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
, reg
->value
, 32);
2512 int xscale_set_reg(reg_t
*reg
, u8
* buf
)
2514 xscale_reg_t
*arch_info
= reg
->arch_info
;
2515 target_t
*target
= arch_info
->target
;
2516 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2517 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2518 u32 value
= buf_get_u32(buf
, 0, 32);
2520 /* DCSR, TX and RX are accessible via JTAG */
2521 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2523 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32, value
);
2524 return xscale_write_dcsr(arch_info
->target
, -1, -1);
2526 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2528 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
2529 return xscale_write_rx(arch_info
->target
);
2531 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2533 /* can't write to TX register (debug-handler -> host) */
2536 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2538 /* can't (explicitly) write to TXRXCTRL register */
2541 else /* Other DBG registers have to be transfered by the debug handler */
2543 /* send CP write request (command 0x41) */
2544 xscale_send_u32(target
, 0x41);
2546 /* send CP register number */
2547 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2549 /* send CP register value */
2550 xscale_send_u32(target
, value
);
2551 buf_set_u32(reg
->value
, 0, 32, value
);
2557 /* convenience wrapper to access XScale specific registers */
2558 int xscale_set_reg_u32(reg_t
*reg
, u32 value
)
2562 buf_set_u32(buf
, 0, 32, value
);
2564 return xscale_set_reg(reg
, buf
);
2567 int xscale_write_dcsr_sw(target_t
*target
, u32 value
)
2569 /* get pointers to arch-specific information */
2570 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2571 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2572 reg_t
*dcsr
= &xscale
->reg_cache
->reg_list
[XSCALE_DCSR
];
2573 xscale_reg_t
*dcsr_arch_info
= dcsr
->arch_info
;
2575 /* send CP write request (command 0x41) */
2576 xscale_send_u32(target
, 0x41);
2578 /* send CP register number */
2579 xscale_send_u32(target
, dcsr_arch_info
->dbg_handler_number
);
2581 /* send CP register value */
2582 xscale_send_u32(target
, value
);
2583 buf_set_u32(dcsr
->value
, 0, 32, value
);
2588 int xscale_read_trace(target_t
*target
)
2590 /* get pointers to arch-specific information */
2591 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2592 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2593 xscale_trace_data_t
**trace_data_p
;
2595 /* 258 words from debug handler
2596 * 256 trace buffer entries
2597 * 2 checkpoint addresses
2599 u32 trace_buffer
[258];
2600 int is_address
[256];
2603 if (target
->state
!= TARGET_HALTED
)
2605 LOG_WARNING("target must be stopped to read trace data");
2606 return ERROR_TARGET_NOT_HALTED
;
2609 /* send read trace buffer command (command 0x61) */
2610 xscale_send_u32(target
, 0x61);
2612 /* receive trace buffer content */
2613 xscale_receive(target
, trace_buffer
, 258);
2615 /* parse buffer backwards to identify address entries */
2616 for (i
= 255; i
>= 0; i
--)
2619 if (((trace_buffer
[i
] & 0xf0) == 0x90) ||
2620 ((trace_buffer
[i
] & 0xf0) == 0xd0))
2623 is_address
[--i
] = 1;
2625 is_address
[--i
] = 1;
2627 is_address
[--i
] = 1;
2629 is_address
[--i
] = 1;
2634 /* search first non-zero entry */
2635 for (j
= 0; (j
< 256) && (trace_buffer
[j
] == 0) && (!is_address
[j
]); j
++)
2640 LOG_DEBUG("no trace data collected");
2641 return ERROR_XSCALE_NO_TRACE_DATA
;
2644 for (trace_data_p
= &xscale
->trace
.data
; *trace_data_p
; trace_data_p
= &(*trace_data_p
)->next
)
2647 *trace_data_p
= malloc(sizeof(xscale_trace_data_t
));
2648 (*trace_data_p
)->next
= NULL
;
2649 (*trace_data_p
)->chkpt0
= trace_buffer
[256];
2650 (*trace_data_p
)->chkpt1
= trace_buffer
[257];
2651 (*trace_data_p
)->last_instruction
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
2652 (*trace_data_p
)->entries
= malloc(sizeof(xscale_trace_entry_t
) * (256 - j
));
2653 (*trace_data_p
)->depth
= 256 - j
;
2655 for (i
= j
; i
< 256; i
++)
2657 (*trace_data_p
)->entries
[i
- j
].data
= trace_buffer
[i
];
2659 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_ADDRESS
;
2661 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_MESSAGE
;
2667 int xscale_read_instruction(target_t
*target
, arm_instruction_t
*instruction
)
2669 /* get pointers to arch-specific information */
2670 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2671 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2678 if (!xscale
->trace
.image
)
2679 return ERROR_TRACE_IMAGE_UNAVAILABLE
;
2681 /* search for the section the current instruction belongs to */
2682 for (i
= 0; i
< xscale
->trace
.image
->num_sections
; i
++)
2684 if ((xscale
->trace
.image
->sections
[i
].base_address
<= xscale
->trace
.current_pc
) &&
2685 (xscale
->trace
.image
->sections
[i
].base_address
+ xscale
->trace
.image
->sections
[i
].size
> xscale
->trace
.current_pc
))
2694 /* current instruction couldn't be found in the image */
2695 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2698 if (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
)
2701 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2702 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2703 4, buf
, &size_read
)) != ERROR_OK
)
2705 LOG_ERROR("error while reading instruction: %i", retval
);
2706 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2708 opcode
= target_buffer_get_u32(target
, buf
);
2709 arm_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2711 else if (xscale
->trace
.core_state
== ARMV4_5_STATE_THUMB
)
2714 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2715 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2716 2, buf
, &size_read
)) != ERROR_OK
)
2718 LOG_ERROR("error while reading instruction: %i", retval
);
2719 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2721 opcode
= target_buffer_get_u16(target
, buf
);
2722 thumb_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2726 LOG_ERROR("BUG: unknown core state encountered");
2733 int xscale_branch_address(xscale_trace_data_t
*trace_data
, int i
, u32
*target
)
2735 /* if there are less than four entries prior to the indirect branch message
2736 * we can't extract the address */
2742 *target
= (trace_data
->entries
[i
-1].data
) | (trace_data
->entries
[i
-2].data
<< 8) |
2743 (trace_data
->entries
[i
-3].data
<< 16) | (trace_data
->entries
[i
-4].data
<< 24);
2748 int xscale_analyze_trace(target_t
*target
, command_context_t
*cmd_ctx
)
2750 /* get pointers to arch-specific information */
2751 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2752 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2755 xscale_trace_data_t
*trace_data
= xscale
->trace
.data
;
2764 xscale
->trace
.core_state
= ARMV4_5_STATE_ARM
;
2769 for (i
= 0; i
< trace_data
->depth
; i
++)
2775 if (trace_data
->entries
[i
].type
== XSCALE_TRACE_ADDRESS
)
2778 switch ((trace_data
->entries
[i
].data
& 0xf0) >> 4)
2780 case 0: /* Exceptions */
2788 exception
= (trace_data
->entries
[i
].data
& 0x70) >> 4;
2790 next_pc
= (trace_data
->entries
[i
].data
& 0xf0) >> 2;
2791 command_print(cmd_ctx
, "--- exception %i ---", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2793 case 8: /* Direct Branch */
2796 case 9: /* Indirect Branch */
2798 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2803 case 13: /* Checkpointed Indirect Branch */
2804 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2807 if (((chkpt
== 0) && (next_pc
!= trace_data
->chkpt0
))
2808 || ((chkpt
== 1) && (next_pc
!= trace_data
->chkpt1
)))
2809 LOG_WARNING("checkpointed indirect branch target address doesn't match checkpoint");
2811 /* explicit fall-through */
2812 case 12: /* Checkpointed Direct Branch */
2817 next_pc
= trace_data
->chkpt0
;
2820 else if (chkpt
== 1)
2823 next_pc
= trace_data
->chkpt0
;
2828 LOG_WARNING("more than two checkpointed branches encountered");
2831 case 15: /* Roll-over */
2834 default: /* Reserved */
2835 command_print(cmd_ctx
, "--- reserved trace message ---");
2836 LOG_ERROR("BUG: trace message %i is reserved", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2840 if (xscale
->trace
.pc_ok
)
2842 int executed
= (trace_data
->entries
[i
].data
& 0xf) + rollover
* 16;
2843 arm_instruction_t instruction
;
2845 if ((exception
== 6) || (exception
== 7))
2847 /* IRQ or FIQ exception, no instruction executed */
2851 while (executed
-- >= 0)
2853 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2855 /* can't continue tracing with no image available */
2856 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2860 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2862 /* TODO: handle incomplete images */
2866 /* a precise abort on a load to the PC is included in the incremental
2867 * word count, other instructions causing data aborts are not included
2869 if ((executed
== 0) && (exception
== 4)
2870 && ((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDM
)))
2872 if ((instruction
.type
== ARM_LDM
)
2873 && ((instruction
.info
.load_store_multiple
.register_list
& 0x8000) == 0))
2877 else if (((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDRSH
))
2878 && (instruction
.info
.load_store
.Rd
!= 15))
2884 /* only the last instruction executed
2885 * (the one that caused the control flow change)
2886 * could be a taken branch
2888 if (((executed
== -1) && (branch
== 1)) &&
2889 (((instruction
.type
== ARM_B
) ||
2890 (instruction
.type
== ARM_BL
) ||
2891 (instruction
.type
== ARM_BLX
)) &&
2892 (instruction
.info
.b_bl_bx_blx
.target_address
!= -1)))
2894 xscale
->trace
.current_pc
= instruction
.info
.b_bl_bx_blx
.target_address
;
2898 xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2;
2900 command_print(cmd_ctx
, "%s", instruction
.text
);
2908 xscale
->trace
.current_pc
= next_pc
;
2909 xscale
->trace
.pc_ok
= 1;
2913 for (; xscale
->trace
.current_pc
< trace_data
->last_instruction
; xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2)
2915 arm_instruction_t instruction
;
2916 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2918 /* can't continue tracing with no image available */
2919 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2923 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2925 /* TODO: handle incomplete images */
2928 command_print(cmd_ctx
, "%s", instruction
.text
);
2931 trace_data
= trace_data
->next
;
2937 void xscale_build_reg_cache(target_t
*target
)
2939 /* get pointers to arch-specific information */
2940 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2941 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2943 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
2944 xscale_reg_t
*arch_info
= malloc(sizeof(xscale_reg_arch_info
));
2946 int num_regs
= sizeof(xscale_reg_arch_info
) / sizeof(xscale_reg_t
);
2948 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
2949 armv4_5
->core_cache
= (*cache_p
);
2951 /* register a register arch-type for XScale dbg registers only once */
2952 if (xscale_reg_arch_type
== -1)
2953 xscale_reg_arch_type
= register_reg_arch_type(xscale_get_reg
, xscale_set_reg
);
2955 (*cache_p
)->next
= malloc(sizeof(reg_cache_t
));
2956 cache_p
= &(*cache_p
)->next
;
2958 /* fill in values for the xscale reg cache */
2959 (*cache_p
)->name
= "XScale registers";
2960 (*cache_p
)->next
= NULL
;
2961 (*cache_p
)->reg_list
= malloc(num_regs
* sizeof(reg_t
));
2962 (*cache_p
)->num_regs
= num_regs
;
2964 for (i
= 0; i
< num_regs
; i
++)
2966 (*cache_p
)->reg_list
[i
].name
= xscale_reg_list
[i
];
2967 (*cache_p
)->reg_list
[i
].value
= calloc(4, 1);
2968 (*cache_p
)->reg_list
[i
].dirty
= 0;
2969 (*cache_p
)->reg_list
[i
].valid
= 0;
2970 (*cache_p
)->reg_list
[i
].size
= 32;
2971 (*cache_p
)->reg_list
[i
].bitfield_desc
= NULL
;
2972 (*cache_p
)->reg_list
[i
].num_bitfields
= 0;
2973 (*cache_p
)->reg_list
[i
].arch_info
= &arch_info
[i
];
2974 (*cache_p
)->reg_list
[i
].arch_type
= xscale_reg_arch_type
;
2975 arch_info
[i
] = xscale_reg_arch_info
[i
];
2976 arch_info
[i
].target
= target
;
2979 xscale
->reg_cache
= (*cache_p
);
2982 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
2993 int xscale_init_arch_info(target_t
*target
, xscale_common_t
*xscale
, int chain_pos
, char *variant
)
2995 armv4_5_common_t
*armv4_5
;
2996 u32 high_reset_branch
, low_reset_branch
;
2999 armv4_5
= &xscale
->armv4_5_common
;
3001 /* store architecture specfic data (none so far) */
3002 xscale
->arch_info
= NULL
;
3003 xscale
->common_magic
= XSCALE_COMMON_MAGIC
;
3005 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
3006 xscale
->variant
= strdup(variant
);
3008 /* prepare JTAG information for the new target */
3009 xscale
->jtag_info
.chain_pos
= chain_pos
;
3011 xscale
->jtag_info
.dbgrx
= 0x02;
3012 xscale
->jtag_info
.dbgtx
= 0x10;
3013 xscale
->jtag_info
.dcsr
= 0x09;
3014 xscale
->jtag_info
.ldic
= 0x07;
3016 if ((strcmp(xscale
->variant
, "pxa250") == 0) ||
3017 (strcmp(xscale
->variant
, "pxa255") == 0) ||
3018 (strcmp(xscale
->variant
, "pxa26x") == 0))
3020 xscale
->jtag_info
.ir_length
= 5;
3022 else if ((strcmp(xscale
->variant
, "pxa27x") == 0) ||
3023 (strcmp(xscale
->variant
, "ixp42x") == 0) ||
3024 (strcmp(xscale
->variant
, "ixp45x") == 0) ||
3025 (strcmp(xscale
->variant
, "ixp46x") == 0))
3027 xscale
->jtag_info
.ir_length
= 7;
3030 /* the debug handler isn't installed (and thus not running) at this time */
3031 xscale
->handler_installed
= 0;
3032 xscale
->handler_running
= 0;
3033 xscale
->handler_address
= 0xfe000800;
3035 /* clear the vectors we keep locally for reference */
3036 memset(xscale
->low_vectors
, 0, sizeof(xscale
->low_vectors
));
3037 memset(xscale
->high_vectors
, 0, sizeof(xscale
->high_vectors
));
3039 /* no user-specified vectors have been configured yet */
3040 xscale
->static_low_vectors_set
= 0x0;
3041 xscale
->static_high_vectors_set
= 0x0;
3043 /* calculate branches to debug handler */
3044 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
3045 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
3047 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
3048 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
3050 for (i
= 1; i
<= 7; i
++)
3052 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3053 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3056 /* 64kB aligned region used for DCache cleaning */
3057 xscale
->cache_clean_address
= 0xfffe0000;
3059 xscale
->hold_rst
= 0;
3060 xscale
->external_debug_break
= 0;
3062 xscale
->force_hw_bkpts
= 1;
3064 xscale
->ibcr_available
= 2;
3065 xscale
->ibcr0_used
= 0;
3066 xscale
->ibcr1_used
= 0;
3068 xscale
->dbr_available
= 2;
3069 xscale
->dbr0_used
= 0;
3070 xscale
->dbr1_used
= 0;
3072 xscale
->arm_bkpt
= ARMV5_BKPT(0x0);
3073 xscale
->thumb_bkpt
= ARMV5_T_BKPT(0x0) & 0xffff;
3075 xscale
->vector_catch
= 0x1;
3077 xscale
->trace
.capture_status
= TRACE_IDLE
;
3078 xscale
->trace
.data
= NULL
;
3079 xscale
->trace
.image
= NULL
;
3080 xscale
->trace
.buffer_enabled
= 0;
3081 xscale
->trace
.buffer_fill
= 0;
3083 /* prepare ARMv4/5 specific information */
3084 armv4_5
->arch_info
= xscale
;
3085 armv4_5
->read_core_reg
= xscale_read_core_reg
;
3086 armv4_5
->write_core_reg
= xscale_write_core_reg
;
3087 armv4_5
->full_context
= xscale_full_context
;
3089 armv4_5_init_arch_info(target
, armv4_5
);
3091 xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
= -1;
3092 xscale
->armv4_5_mmu
.get_ttb
= xscale_get_ttb
;
3093 xscale
->armv4_5_mmu
.read_memory
= xscale_read_memory
;
3094 xscale
->armv4_5_mmu
.write_memory
= xscale_write_memory
;
3095 xscale
->armv4_5_mmu
.disable_mmu_caches
= xscale_disable_mmu_caches
;
3096 xscale
->armv4_5_mmu
.enable_mmu_caches
= xscale_enable_mmu_caches
;
3097 xscale
->armv4_5_mmu
.has_tiny_pages
= 1;
3098 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3103 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
3104 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
)
3107 char *variant
= NULL
;
3108 xscale_common_t
*xscale
= malloc(sizeof(xscale_common_t
));
3109 memset(xscale
, 0, sizeof(*xscale
));
3113 LOG_ERROR("'target xscale' requires four arguments: <endianess> <startup_mode> <chain_pos> <variant>");
3117 chain_pos
= strtoul(args
[3], NULL
, 0);
3121 xscale_init_arch_info(target
, xscale
, chain_pos
, variant
);
3122 xscale_build_reg_cache(target
);
3127 int xscale_handle_debug_handler_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3129 target_t
*target
= NULL
;
3130 armv4_5_common_t
*armv4_5
;
3131 xscale_common_t
*xscale
;
3133 u32 handler_address
;
3137 LOG_ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
3141 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3143 LOG_ERROR("no target '%s' configured", args
[0]);
3147 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3152 handler_address
= strtoul(args
[1], NULL
, 0);
3154 if (((handler_address
>= 0x800) && (handler_address
<= 0x1fef800)) ||
3155 ((handler_address
>= 0xfe000800) && (handler_address
<= 0xfffff800)))
3157 xscale
->handler_address
= handler_address
;
3161 LOG_ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
3167 int xscale_handle_cache_clean_address_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3169 target_t
*target
= NULL
;
3170 armv4_5_common_t
*armv4_5
;
3171 xscale_common_t
*xscale
;
3173 u32 cache_clean_address
;
3177 LOG_ERROR("'xscale cache_clean_address <target#> <address>' command takes two required operands");
3181 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3183 LOG_ERROR("no target '%s' configured", args
[0]);
3187 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3192 cache_clean_address
= strtoul(args
[1], NULL
, 0);
3194 if (cache_clean_address
& 0xffff)
3196 LOG_ERROR("xscale cache_clean_address <address> must be 64kb aligned");
3200 xscale
->cache_clean_address
= cache_clean_address
;
3206 int xscale_handle_cache_info_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3208 target_t
*target
= get_current_target(cmd_ctx
);
3209 armv4_5_common_t
*armv4_5
;
3210 xscale_common_t
*xscale
;
3212 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3217 return armv4_5_handle_cache_info_command(cmd_ctx
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
3220 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
)
3222 armv4_5_common_t
*armv4_5
;
3223 xscale_common_t
*xscale
;
3231 if ((retval
= xscale_get_arch_pointers(target
, &armv4_5
, &xscale
)) != ERROR_OK
)
3235 u32 ret
= armv4_5_mmu_translate_va(target
, &xscale
->armv4_5_mmu
, virtual, &type
, &cb
, &domain
, &ap
);
3244 static int xscale_mmu(struct target_s
*target
, int *enabled
)
3246 armv4_5_common_t
*armv4_5
= target
->arch_info
;
3247 xscale_common_t
*xscale
= armv4_5
->arch_info
;
3249 if (target
->state
!= TARGET_HALTED
)
3251 LOG_ERROR("Target not halted");
3252 return ERROR_TARGET_INVALID
;
3254 *enabled
= xscale
->armv4_5_mmu
.mmu_enabled
;
3259 int xscale_handle_mmu_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3261 target_t
*target
= get_current_target(cmd_ctx
);
3262 armv4_5_common_t
*armv4_5
;
3263 xscale_common_t
*xscale
;
3265 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3270 if (target
->state
!= TARGET_HALTED
)
3272 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3278 if (strcmp("enable", args
[0]) == 0)
3280 xscale_enable_mmu_caches(target
, 1, 0, 0);
3281 xscale
->armv4_5_mmu
.mmu_enabled
= 1;
3283 else if (strcmp("disable", args
[0]) == 0)
3285 xscale_disable_mmu_caches(target
, 1, 0, 0);
3286 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3290 command_print(cmd_ctx
, "mmu %s", (xscale
->armv4_5_mmu
.mmu_enabled
) ? "enabled" : "disabled");
3295 int xscale_handle_idcache_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3297 target_t
*target
= get_current_target(cmd_ctx
);
3298 armv4_5_common_t
*armv4_5
;
3299 xscale_common_t
*xscale
;
3300 int icache
= 0, dcache
= 0;
3302 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3307 if (target
->state
!= TARGET_HALTED
)
3309 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3313 if (strcmp(cmd
, "icache") == 0)
3315 else if (strcmp(cmd
, "dcache") == 0)
3320 if (strcmp("enable", args
[0]) == 0)
3322 xscale_enable_mmu_caches(target
, 0, dcache
, icache
);
3325 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 1;
3327 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 1;
3329 else if (strcmp("disable", args
[0]) == 0)
3331 xscale_disable_mmu_caches(target
, 0, dcache
, icache
);
3334 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 0;
3336 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 0;
3341 command_print(cmd_ctx
, "icache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
) ? "enabled" : "disabled");
3344 command_print(cmd_ctx
, "dcache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
) ? "enabled" : "disabled");
3349 int xscale_handle_vector_catch_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3351 target_t
*target
= get_current_target(cmd_ctx
);
3352 armv4_5_common_t
*armv4_5
;
3353 xscale_common_t
*xscale
;
3355 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3362 command_print(cmd_ctx
, "usage: xscale vector_catch [mask]");
3366 xscale
->vector_catch
= strtoul(args
[0], NULL
, 0);
3367 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 8, xscale
->vector_catch
);
3368 xscale_write_dcsr(target
, -1, -1);
3371 command_print(cmd_ctx
, "vector catch mask: 0x%2.2x", xscale
->vector_catch
);
3376 int xscale_handle_force_hw_bkpts_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3378 target_t
*target
= get_current_target(cmd_ctx
);
3379 armv4_5_common_t
*armv4_5
;
3380 xscale_common_t
*xscale
;
3382 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3387 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3389 xscale
->force_hw_bkpts
= 1;
3391 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3393 xscale
->force_hw_bkpts
= 0;
3397 command_print(cmd_ctx
, "usage: xscale force_hw_bkpts <enable|disable>");
3400 command_print(cmd_ctx
, "force hardware breakpoints %s", (xscale
->force_hw_bkpts
) ? "enabled" : "disabled");
3405 int xscale_handle_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3407 target_t
*target
= get_current_target(cmd_ctx
);
3408 armv4_5_common_t
*armv4_5
;
3409 xscale_common_t
*xscale
;
3412 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3417 if (target
->state
!= TARGET_HALTED
)
3419 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3423 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3425 xscale_trace_data_t
*td
, *next_td
;
3426 xscale
->trace
.buffer_enabled
= 1;
3428 /* free old trace data */
3429 td
= xscale
->trace
.data
;
3439 xscale
->trace
.data
= NULL
;
3441 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3443 xscale
->trace
.buffer_enabled
= 0;
3446 if ((argc
>= 2) && (strcmp("fill", args
[1]) == 0))
3449 xscale
->trace
.buffer_fill
= strtoul(args
[2], NULL
, 0);
3451 xscale
->trace
.buffer_fill
= 1;
3453 else if ((argc
>= 2) && (strcmp("wrap", args
[1]) == 0))
3455 xscale
->trace
.buffer_fill
= -1;
3458 if (xscale
->trace
.buffer_enabled
)
3460 /* if we enable the trace buffer in fill-once
3461 * mode we know the address of the first instruction */
3462 xscale
->trace
.pc_ok
= 1;
3463 xscale
->trace
.current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
3467 /* otherwise the address is unknown, and we have no known good PC */
3468 xscale
->trace
.pc_ok
= 0;
3471 command_print(cmd_ctx
, "trace buffer %s (%s)",
3472 (xscale
->trace
.buffer_enabled
) ? "enabled" : "disabled",
3473 (xscale
->trace
.buffer_fill
> 0) ? "fill" : "wrap");
3475 dcsr_value
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32);
3476 if (xscale
->trace
.buffer_fill
>= 0)
3477 xscale_write_dcsr_sw(target
, (dcsr_value
& 0xfffffffc) | 2);
3479 xscale_write_dcsr_sw(target
, dcsr_value
& 0xfffffffc);
3484 int xscale_handle_trace_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3487 armv4_5_common_t
*armv4_5
;
3488 xscale_common_t
*xscale
;
3492 command_print(cmd_ctx
, "usage: xscale trace_image <file> [base address] [type]");
3496 target
= get_current_target(cmd_ctx
);
3498 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3503 if (xscale
->trace
.image
)
3505 image_close(xscale
->trace
.image
);
3506 free(xscale
->trace
.image
);
3507 command_print(cmd_ctx
, "previously loaded image found and closed");
3510 xscale
->trace
.image
= malloc(sizeof(image_t
));
3511 xscale
->trace
.image
->base_address_set
= 0;
3512 xscale
->trace
.image
->start_address_set
= 0;
3514 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
3517 xscale
->trace
.image
->base_address_set
= 1;
3518 xscale
->trace
.image
->base_address
= strtoul(args
[1], NULL
, 0);
3522 xscale
->trace
.image
->base_address_set
= 0;
3525 if (image_open(xscale
->trace
.image
, args
[0], (argc
>= 3) ? args
[2] : NULL
) != ERROR_OK
)
3527 free(xscale
->trace
.image
);
3528 xscale
->trace
.image
= NULL
;
3535 int xscale_handle_dump_trace_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3537 target_t
*target
= get_current_target(cmd_ctx
);
3538 armv4_5_common_t
*armv4_5
;
3539 xscale_common_t
*xscale
;
3540 xscale_trace_data_t
*trace_data
;
3543 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3548 if (target
->state
!= TARGET_HALTED
)
3550 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3556 command_print(cmd_ctx
, "usage: xscale dump_trace <file>");
3560 trace_data
= xscale
->trace
.data
;
3564 command_print(cmd_ctx
, "no trace data collected");
3568 if (fileio_open(&file
, args
[0], FILEIO_WRITE
, FILEIO_BINARY
) != ERROR_OK
)
3577 fileio_write_u32(&file
, trace_data
->chkpt0
);
3578 fileio_write_u32(&file
, trace_data
->chkpt1
);
3579 fileio_write_u32(&file
, trace_data
->last_instruction
);
3580 fileio_write_u32(&file
, trace_data
->depth
);
3582 for (i
= 0; i
< trace_data
->depth
; i
++)
3583 fileio_write_u32(&file
, trace_data
->entries
[i
].data
| ((trace_data
->entries
[i
].type
& 0xffff) << 16));
3585 trace_data
= trace_data
->next
;
3588 fileio_close(&file
);
3593 int xscale_handle_analyze_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3595 target_t
*target
= get_current_target(cmd_ctx
);
3596 armv4_5_common_t
*armv4_5
;
3597 xscale_common_t
*xscale
;
3599 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3604 xscale_analyze_trace(target
, cmd_ctx
);
3609 int xscale_handle_cp15(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3611 target_t
*target
= get_current_target(cmd_ctx
);
3612 armv4_5_common_t
*armv4_5
;
3613 xscale_common_t
*xscale
;
3615 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3620 if (target
->state
!= TARGET_HALTED
)
3622 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3629 reg_no
= strtoul(args
[0], NULL
, 0);
3630 /*translate from xscale cp15 register no to openocd register*/
3634 reg_no
= XSCALE_MAINID
;
3637 reg_no
= XSCALE_CTRL
;
3640 reg_no
= XSCALE_TTB
;
3643 reg_no
= XSCALE_DAC
;
3646 reg_no
= XSCALE_FSR
;
3649 reg_no
= XSCALE_FAR
;
3652 reg_no
= XSCALE_PID
;
3655 reg_no
= XSCALE_CPACCESS
;
3658 command_print(cmd_ctx
, "invalid register number");
3659 return ERROR_INVALID_ARGUMENTS
;
3661 reg
= &xscale
->reg_cache
->reg_list
[reg_no
];
3668 /* read cp15 control register */
3669 xscale_get_reg(reg
);
3670 value
= buf_get_u32(reg
->value
, 0, 32);
3671 command_print(cmd_ctx
, "%s (/%i): 0x%x", reg
->name
, reg
->size
, value
);
3676 u32 value
= strtoul(args
[1], NULL
, 0);
3678 /* send CP write request (command 0x41) */
3679 xscale_send_u32(target
, 0x41);
3681 /* send CP register number */
3682 xscale_send_u32(target
, reg_no
);
3684 /* send CP register value */
3685 xscale_send_u32(target
, value
);
3687 /* execute cpwait to ensure outstanding operations complete */
3688 xscale_send_u32(target
, 0x53);
3692 command_print(cmd_ctx
, "usage: cp15 [register]<, [value]>");
3698 int xscale_register_commands(struct command_context_s
*cmd_ctx
)
3700 command_t
*xscale_cmd
;
3702 xscale_cmd
= register_command(cmd_ctx
, NULL
, "xscale", NULL
, COMMAND_ANY
, "xscale specific commands");
3704 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");
3705 register_command(cmd_ctx
, xscale_cmd
, "cache_clean_address", xscale_handle_cache_clean_address_command
, COMMAND_ANY
, NULL
);
3707 register_command(cmd_ctx
, xscale_cmd
, "cache_info", xscale_handle_cache_info_command
, COMMAND_EXEC
, NULL
);
3708 register_command(cmd_ctx
, xscale_cmd
, "mmu", xscale_handle_mmu_command
, COMMAND_EXEC
, "['enable'|'disable'] the MMU");
3709 register_command(cmd_ctx
, xscale_cmd
, "icache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the ICache");
3710 register_command(cmd_ctx
, xscale_cmd
, "dcache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the DCache");
3712 register_command(cmd_ctx
, xscale_cmd
, "vector_catch", xscale_handle_idcache_command
, COMMAND_EXEC
, "<mask> of vectors that should be catched");
3714 register_command(cmd_ctx
, xscale_cmd
, "trace_buffer", xscale_handle_trace_buffer_command
, COMMAND_EXEC
, "<enable|disable> ['fill' [n]|'wrap']");
3716 register_command(cmd_ctx
, xscale_cmd
, "dump_trace", xscale_handle_dump_trace_command
, COMMAND_EXEC
, "dump content of trace buffer to <file>");
3717 register_command(cmd_ctx
, xscale_cmd
, "analyze_trace", xscale_handle_analyze_trace_buffer_command
, COMMAND_EXEC
, "analyze content of trace buffer");
3718 register_command(cmd_ctx
, xscale_cmd
, "trace_image", xscale_handle_trace_image_command
,
3719 COMMAND_EXEC
, "load image from <file> [base address]");
3721 register_command(cmd_ctx
, xscale_cmd
, "cp15", xscale_handle_cp15
, COMMAND_EXEC
, "access coproc 15 <register> [value]");
3723 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)