1 /***************************************************************************
2 * Copyright (C) 2006, 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * Copyright (C) 2007,2008 Øyvind Harboe *
6 * oyvind.harboe@zylin.com *
8 * This program is free software; you can redistribute it and/or modify *
9 * it under the terms of the GNU General Public License as published by *
10 * the Free Software Foundation; either version 2 of the License, or *
11 * (at your option) any later version. *
13 * This program is distributed in the hope that it will be useful, *
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
16 * GNU General Public License for more details. *
18 * You should have received a copy of the GNU General Public License *
19 * along with this program; if not, write to the *
20 * Free Software Foundation, Inc., *
21 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
22 ***************************************************************************/
27 #include "replacements.h"
31 #include "arm7_9_common.h"
35 #include "arm_simulator.h"
36 #include "arm_disassembler.h"
39 #include "binarybuffer.h"
40 #include "time_support.h"
41 #include "breakpoints.h"
47 #include <sys/types.h>
53 int xscale_register_commands(struct command_context_s
*cmd_ctx
);
55 /* forward declarations */
56 int xscale_target_create(struct target_s
*target
, Jim_Interp
*interp
);
57 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
58 int xscale_quit(void);
60 int xscale_arch_state(struct target_s
*target
);
61 int xscale_poll(target_t
*target
);
62 int xscale_halt(target_t
*target
);
63 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
);
64 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
);
65 int xscale_debug_entry(target_t
*target
);
66 int xscale_restore_context(target_t
*target
);
68 int xscale_assert_reset(target_t
*target
);
69 int xscale_deassert_reset(target_t
*target
);
70 int xscale_soft_reset_halt(struct target_s
*target
);
72 int xscale_set_reg_u32(reg_t
*reg
, u32 value
);
74 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
);
75 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
);
77 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
78 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
79 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
);
81 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
82 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
83 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
84 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
85 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
86 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
87 void xscale_enable_watchpoints(struct target_s
*target
);
88 void xscale_enable_breakpoints(struct target_s
*target
);
89 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
);
90 static int xscale_mmu(struct target_s
*target
, int *enabled
);
92 int xscale_read_trace(target_t
*target
);
94 target_type_t xscale_target
=
99 .arch_state
= xscale_arch_state
,
101 .target_request_data
= NULL
,
104 .resume
= xscale_resume
,
107 .assert_reset
= xscale_assert_reset
,
108 .deassert_reset
= xscale_deassert_reset
,
109 .soft_reset_halt
= xscale_soft_reset_halt
,
111 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
113 .read_memory
= xscale_read_memory
,
114 .write_memory
= xscale_write_memory
,
115 .bulk_write_memory
= xscale_bulk_write_memory
,
116 .checksum_memory
= arm7_9_checksum_memory
,
117 .blank_check_memory
= arm7_9_blank_check_memory
,
119 .run_algorithm
= armv4_5_run_algorithm
,
121 .add_breakpoint
= xscale_add_breakpoint
,
122 .remove_breakpoint
= xscale_remove_breakpoint
,
123 .add_watchpoint
= xscale_add_watchpoint
,
124 .remove_watchpoint
= xscale_remove_watchpoint
,
126 .register_commands
= xscale_register_commands
,
127 .target_create
= xscale_target_create
,
128 .init_target
= xscale_init_target
,
131 .virt2phys
= xscale_virt2phys
,
135 char* xscale_reg_list
[] =
137 "XSCALE_MAINID", /* 0 */
147 "XSCALE_IBCR0", /* 10 */
157 "XSCALE_RX", /* 20 */
161 xscale_reg_t xscale_reg_arch_info
[] =
163 {XSCALE_MAINID
, NULL
},
164 {XSCALE_CACHETYPE
, NULL
},
166 {XSCALE_AUXCTRL
, NULL
},
172 {XSCALE_CPACCESS
, NULL
},
173 {XSCALE_IBCR0
, NULL
},
174 {XSCALE_IBCR1
, NULL
},
177 {XSCALE_DBCON
, NULL
},
178 {XSCALE_TBREG
, NULL
},
179 {XSCALE_CHKPT0
, NULL
},
180 {XSCALE_CHKPT1
, NULL
},
181 {XSCALE_DCSR
, NULL
}, /* DCSR accessed via JTAG or SW */
182 {-1, NULL
}, /* TX accessed via JTAG */
183 {-1, NULL
}, /* RX accessed via JTAG */
184 {-1, NULL
}, /* TXRXCTRL implicit access via JTAG */
187 int xscale_reg_arch_type
= -1;
189 int xscale_get_reg(reg_t
*reg
);
190 int xscale_set_reg(reg_t
*reg
, u8
*buf
);
192 int xscale_get_arch_pointers(target_t
*target
, armv4_5_common_t
**armv4_5_p
, xscale_common_t
**xscale_p
)
194 armv4_5_common_t
*armv4_5
= target
->arch_info
;
195 xscale_common_t
*xscale
= armv4_5
->arch_info
;
197 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
199 LOG_ERROR("target isn't an XScale target");
203 if (xscale
->common_magic
!= XSCALE_COMMON_MAGIC
)
205 LOG_ERROR("target isn't an XScale target");
209 *armv4_5_p
= armv4_5
;
215 int xscale_jtag_set_instr(jtag_tap_t
*tap
, u32 new_instr
)
220 if (buf_get_u32(tap
->cur_instr
, 0, tap
->ir_length
) != new_instr
)
225 field
.num_bits
= tap
->ir_length
;
226 field
.out_value
= calloc(CEIL(field
.num_bits
, 8), 1);
227 buf_set_u32(field
.out_value
, 0, field
.num_bits
, new_instr
);
228 field
.out_mask
= NULL
;
229 field
.in_value
= NULL
;
230 jtag_set_check_value(&field
, tap
->expected
, tap
->expected_mask
, NULL
);
232 jtag_add_ir_scan(1, &field
, -1);
234 free(field
.out_value
);
240 int xscale_read_dcsr(target_t
*target
)
242 armv4_5_common_t
*armv4_5
= target
->arch_info
;
243 xscale_common_t
*xscale
= armv4_5
->arch_info
;
247 scan_field_t fields
[3];
249 u8 field0_check_value
= 0x2;
250 u8 field0_check_mask
= 0x7;
252 u8 field2_check_value
= 0x0;
253 u8 field2_check_mask
= 0x1;
255 jtag_add_end_state(TAP_DRPAUSE
);
256 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
258 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
259 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
261 fields
[0].tap
= xscale
->jtag_info
.tap
;
262 fields
[0].num_bits
= 3;
263 fields
[0].out_value
= &field0
;
264 fields
[0].out_mask
= NULL
;
265 fields
[0].in_value
= NULL
;
266 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
268 fields
[1].tap
= xscale
->jtag_info
.tap
;
269 fields
[1].num_bits
= 32;
270 fields
[1].out_value
= NULL
;
271 fields
[1].out_mask
= NULL
;
272 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
273 fields
[1].in_handler
= NULL
;
274 fields
[1].in_handler_priv
= NULL
;
275 fields
[1].in_check_value
= NULL
;
276 fields
[1].in_check_mask
= NULL
;
278 fields
[2].tap
= xscale
->jtag_info
.tap
;
279 fields
[2].num_bits
= 1;
280 fields
[2].out_value
= &field2
;
281 fields
[2].out_mask
= NULL
;
282 fields
[2].in_value
= NULL
;
283 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
285 jtag_add_dr_scan(3, fields
, -1);
287 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
289 LOG_ERROR("JTAG error while reading DCSR");
293 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
294 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
296 /* write the register with the value we just read
297 * on this second pass, only the first bit of field0 is guaranteed to be 0)
299 field0_check_mask
= 0x1;
300 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
301 fields
[1].in_value
= NULL
;
303 jtag_add_end_state(TAP_IDLE
);
305 jtag_add_dr_scan(3, fields
, -1);
307 /* DANGER!!! this must be here. It will make sure that the arguments
308 * to jtag_set_check_value() does not go out of scope! */
309 return jtag_execute_queue();
312 int xscale_receive(target_t
*target
, u32
*buffer
, int num_words
)
315 return ERROR_INVALID_ARGUMENTS
;
318 armv4_5_common_t
*armv4_5
= target
->arch_info
;
319 xscale_common_t
*xscale
= armv4_5
->arch_info
;
321 enum tap_state path
[3];
322 scan_field_t fields
[3];
324 u8
*field0
= malloc(num_words
* 1);
325 u8 field0_check_value
= 0x2;
326 u8 field0_check_mask
= 0x6;
327 u32
*field1
= malloc(num_words
* 4);
328 u8 field2_check_value
= 0x0;
329 u8 field2_check_mask
= 0x1;
331 int words_scheduled
= 0;
335 path
[0] = TAP_DRSELECT
;
336 path
[1] = TAP_DRCAPTURE
;
337 path
[2] = TAP_DRSHIFT
;
339 fields
[0].tap
= xscale
->jtag_info
.tap
;
340 fields
[0].num_bits
= 3;
341 fields
[0].out_value
= NULL
;
342 fields
[0].out_mask
= NULL
;
343 fields
[0].in_value
= NULL
;
344 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
346 fields
[1].tap
= xscale
->jtag_info
.tap
;
347 fields
[1].num_bits
= 32;
348 fields
[1].out_value
= NULL
;
349 fields
[1].out_mask
= NULL
;
350 fields
[1].in_value
= NULL
;
351 fields
[1].in_handler
= NULL
;
352 fields
[1].in_handler_priv
= NULL
;
353 fields
[1].in_check_value
= NULL
;
354 fields
[1].in_check_mask
= NULL
;
356 fields
[2].tap
= xscale
->jtag_info
.tap
;
357 fields
[2].num_bits
= 1;
358 fields
[2].out_value
= NULL
;
359 fields
[2].out_mask
= NULL
;
360 fields
[2].in_value
= NULL
;
361 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
363 jtag_add_end_state(TAP_IDLE
);
364 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgtx
);
365 jtag_add_runtest(1, -1); /* ensures that we're in the TAP_IDLE state as the above could be a no-op */
367 /* repeat until all words have been collected */
369 while (words_done
< num_words
)
373 for (i
= words_done
; i
< num_words
; i
++)
375 fields
[0].in_value
= &field0
[i
];
376 fields
[1].in_handler
= buf_to_u32_handler
;
377 fields
[1].in_handler_priv
= (u8
*)&field1
[i
];
379 jtag_add_pathmove(3, path
);
380 jtag_add_dr_scan(3, fields
, TAP_IDLE
);
384 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
386 LOG_ERROR("JTAG error while receiving data from debug handler");
390 /* examine results */
391 for (i
= words_done
; i
< num_words
; i
++)
393 if (!(field0
[0] & 1))
395 /* move backwards if necessary */
397 for (j
= i
; j
< num_words
- 1; j
++)
399 field0
[j
] = field0
[j
+1];
400 field1
[j
] = field1
[j
+1];
405 if (words_scheduled
==0)
407 if (attempts
++==1000)
409 LOG_ERROR("Failed to receiving data from debug handler after 1000 attempts");
410 retval
=ERROR_TARGET_TIMEOUT
;
415 words_done
+= words_scheduled
;
418 for (i
= 0; i
< num_words
; i
++)
419 *(buffer
++) = buf_get_u32((u8
*)&field1
[i
], 0, 32);
426 int xscale_read_tx(target_t
*target
, int consume
)
428 armv4_5_common_t
*armv4_5
= target
->arch_info
;
429 xscale_common_t
*xscale
= armv4_5
->arch_info
;
430 enum tap_state path
[3];
431 enum tap_state noconsume_path
[6];
434 struct timeval timeout
, now
;
436 scan_field_t fields
[3];
438 u8 field0_check_value
= 0x2;
439 u8 field0_check_mask
= 0x6;
440 u8 field2_check_value
= 0x0;
441 u8 field2_check_mask
= 0x1;
443 jtag_add_end_state(TAP_IDLE
);
445 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgtx
);
447 path
[0] = TAP_DRSELECT
;
448 path
[1] = TAP_DRCAPTURE
;
449 path
[2] = TAP_DRSHIFT
;
451 noconsume_path
[0] = TAP_DRSELECT
;
452 noconsume_path
[1] = TAP_DRCAPTURE
;
453 noconsume_path
[2] = TAP_DREXIT1
;
454 noconsume_path
[3] = TAP_DRPAUSE
;
455 noconsume_path
[4] = TAP_DREXIT2
;
456 noconsume_path
[5] = TAP_DRSHIFT
;
458 fields
[0].tap
= xscale
->jtag_info
.tap
;
459 fields
[0].num_bits
= 3;
460 fields
[0].out_value
= NULL
;
461 fields
[0].out_mask
= NULL
;
462 fields
[0].in_value
= &field0_in
;
463 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
465 fields
[1].tap
= xscale
->jtag_info
.tap
;
466 fields
[1].num_bits
= 32;
467 fields
[1].out_value
= NULL
;
468 fields
[1].out_mask
= NULL
;
469 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
;
470 fields
[1].in_handler
= NULL
;
471 fields
[1].in_handler_priv
= NULL
;
472 fields
[1].in_check_value
= NULL
;
473 fields
[1].in_check_mask
= NULL
;
475 fields
[2].tap
= xscale
->jtag_info
.tap
;
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);
487 /* if we want to consume the register content (i.e. clear TX_READY),
488 * we have to go straight from Capture-DR to Shift-DR
489 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
492 jtag_add_pathmove(3, path
);
495 jtag_add_pathmove(sizeof(noconsume_path
)/sizeof(*noconsume_path
), noconsume_path
);
498 jtag_add_dr_scan(3, fields
, TAP_IDLE
);
500 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
502 LOG_ERROR("JTAG error while reading TX");
503 return ERROR_TARGET_TIMEOUT
;
506 gettimeofday(&now
, NULL
);
507 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
509 LOG_ERROR("time out reading TX register");
510 return ERROR_TARGET_TIMEOUT
;
512 if (!((!(field0_in
& 1)) && consume
))
518 LOG_DEBUG("waiting 100ms");
519 alive_sleep(100); /* avoid flooding the logs */
527 if (!(field0_in
& 1))
528 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
533 int xscale_write_rx(target_t
*target
)
535 armv4_5_common_t
*armv4_5
= target
->arch_info
;
536 xscale_common_t
*xscale
= armv4_5
->arch_info
;
539 struct timeval timeout
, now
;
541 scan_field_t fields
[3];
544 u8 field0_check_value
= 0x2;
545 u8 field0_check_mask
= 0x6;
547 u8 field2_check_value
= 0x0;
548 u8 field2_check_mask
= 0x1;
550 jtag_add_end_state(TAP_IDLE
);
552 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgrx
);
554 fields
[0].tap
= xscale
->jtag_info
.tap
;
555 fields
[0].num_bits
= 3;
556 fields
[0].out_value
= &field0_out
;
557 fields
[0].out_mask
= NULL
;
558 fields
[0].in_value
= &field0_in
;
559 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
561 fields
[1].tap
= xscale
->jtag_info
.tap
;
562 fields
[1].num_bits
= 32;
563 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
;
564 fields
[1].out_mask
= NULL
;
565 fields
[1].in_value
= NULL
;
566 fields
[1].in_handler
= NULL
;
567 fields
[1].in_handler_priv
= NULL
;
568 fields
[1].in_check_value
= NULL
;
569 fields
[1].in_check_mask
= NULL
;
571 fields
[2].tap
= xscale
->jtag_info
.tap
;
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");
585 jtag_add_dr_scan(3, fields
, TAP_IDLE
);
587 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
589 LOG_ERROR("JTAG error while writing RX");
593 gettimeofday(&now
, NULL
);
594 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
596 LOG_ERROR("time out writing RX register");
597 return ERROR_TARGET_TIMEOUT
;
599 if (!(field0_in
& 1))
603 LOG_DEBUG("waiting 100ms");
604 alive_sleep(100); /* avoid flooding the logs */
614 jtag_add_dr_scan(3, fields
, TAP_IDLE
);
616 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
618 LOG_ERROR("JTAG error while writing RX");
625 /* send count elements of size byte to the debug handler */
626 int xscale_send(target_t
*target
, u8
*buffer
, int count
, int size
)
628 armv4_5_common_t
*armv4_5
= target
->arch_info
;
629 xscale_common_t
*xscale
= armv4_5
->arch_info
;
637 jtag_add_end_state(TAP_IDLE
);
639 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dbgrx
);
646 int endianness
= target
->endianness
;
647 while (done_count
++ < count
)
652 if (endianness
== TARGET_LITTLE_ENDIAN
)
654 t
[1]=le_to_h_u32(buffer
);
657 t
[1]=be_to_h_u32(buffer
);
661 if (endianness
== TARGET_LITTLE_ENDIAN
)
663 t
[1]=le_to_h_u16(buffer
);
666 t
[1]=be_to_h_u16(buffer
);
673 LOG_ERROR("BUG: size neither 4, 2 nor 1");
676 jtag_add_dr_out(xscale
->jtag_info
.tap
,
684 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
686 LOG_ERROR("JTAG error while sending data to debug handler");
693 int xscale_send_u32(target_t
*target
, u32 value
)
695 armv4_5_common_t
*armv4_5
= target
->arch_info
;
696 xscale_common_t
*xscale
= armv4_5
->arch_info
;
698 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
699 return xscale_write_rx(target
);
702 int xscale_write_dcsr(target_t
*target
, int hold_rst
, int ext_dbg_brk
)
704 armv4_5_common_t
*armv4_5
= target
->arch_info
;
705 xscale_common_t
*xscale
= armv4_5
->arch_info
;
709 scan_field_t fields
[3];
711 u8 field0_check_value
= 0x2;
712 u8 field0_check_mask
= 0x7;
714 u8 field2_check_value
= 0x0;
715 u8 field2_check_mask
= 0x1;
718 xscale
->hold_rst
= hold_rst
;
720 if (ext_dbg_brk
!= -1)
721 xscale
->external_debug_break
= ext_dbg_brk
;
723 jtag_add_end_state(TAP_IDLE
);
724 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
726 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
727 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
729 fields
[0].tap
= xscale
->jtag_info
.tap
;
730 fields
[0].num_bits
= 3;
731 fields
[0].out_value
= &field0
;
732 fields
[0].out_mask
= NULL
;
733 fields
[0].in_value
= NULL
;
734 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
736 fields
[1].tap
= xscale
->jtag_info
.tap
;
737 fields
[1].num_bits
= 32;
738 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
739 fields
[1].out_mask
= NULL
;
740 fields
[1].in_value
= NULL
;
741 fields
[1].in_handler
= NULL
;
742 fields
[1].in_handler_priv
= NULL
;
743 fields
[1].in_check_value
= NULL
;
744 fields
[1].in_check_mask
= NULL
;
746 fields
[2].tap
= xscale
->jtag_info
.tap
;
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_IDLE
);
792 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, 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].tap
= xscale
->jtag_info
.tap
;
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].tap
= xscale
->jtag_info
.tap
;
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_IDLE
);
855 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, 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].tap
= xscale
->jtag_info
.tap
;
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].tap
= xscale
->jtag_info
.tap
;
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 Jim_Nvp_value2name_simple( nvp_target_debug_reason
, target
->debug_reason
)->name
,
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",
1222 Jim_Nvp_value2name_simple( nvp_target_state
, target
->state
)->name
);
1224 if (target
->state
== TARGET_HALTED
)
1226 LOG_DEBUG("target was already halted");
1229 else if (target
->state
== TARGET_UNKNOWN
)
1231 /* this must not happen for a xscale target */
1232 LOG_ERROR("target was in unknown state when halt was requested");
1233 return ERROR_TARGET_INVALID
;
1235 else if (target
->state
== TARGET_RESET
)
1237 LOG_DEBUG("target->state == TARGET_RESET");
1241 /* assert external dbg break */
1242 xscale
->external_debug_break
= 1;
1243 xscale_read_dcsr(target
);
1245 target
->debug_reason
= DBG_REASON_DBGRQ
;
1251 int xscale_enable_single_step(struct target_s
*target
, u32 next_pc
)
1253 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1254 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1255 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1258 if (xscale
->ibcr0_used
)
1260 breakpoint_t
*ibcr0_bp
= breakpoint_find(target
, buf_get_u32(ibcr0
->value
, 0, 32) & 0xfffffffe);
1264 xscale_unset_breakpoint(target
, ibcr0_bp
);
1268 LOG_ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1273 if ((retval
=xscale_set_reg_u32(ibcr0
, next_pc
| 0x1))!=ERROR_OK
)
1279 int xscale_disable_single_step(struct target_s
*target
)
1281 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1282 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1283 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1286 if ((retval
=xscale_set_reg_u32(ibcr0
, 0x0))!=ERROR_OK
)
1292 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
)
1294 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1295 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1296 breakpoint_t
*breakpoint
= target
->breakpoints
;
1305 if (target
->state
!= TARGET_HALTED
)
1307 LOG_WARNING("target not halted");
1308 return ERROR_TARGET_NOT_HALTED
;
1311 if (!debug_execution
)
1313 target_free_all_working_areas(target
);
1316 /* update vector tables */
1317 if ((retval
=xscale_update_vectors(target
))!=ERROR_OK
)
1320 /* current = 1: continue on current pc, otherwise continue at <address> */
1322 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1324 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1326 /* if we're at the reset vector, we have to simulate the branch */
1327 if (current_pc
== 0x0)
1329 arm_simulate_step(target
, NULL
);
1330 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1333 /* the front-end may request us not to handle breakpoints */
1334 if (handle_breakpoints
)
1336 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1340 /* there's a breakpoint at the current PC, we have to step over it */
1341 LOG_DEBUG("unset breakpoint at 0x%8.8x", breakpoint
->address
);
1342 xscale_unset_breakpoint(target
, breakpoint
);
1344 /* calculate PC of next instruction */
1345 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1348 target_read_u32(target
, current_pc
, ¤t_opcode
);
1349 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1352 LOG_DEBUG("enable single-step");
1353 xscale_enable_single_step(target
, next_pc
);
1355 /* restore banked registers */
1356 xscale_restore_context(target
);
1358 /* send resume request (command 0x30 or 0x31)
1359 * clean the trace buffer if it is to be enabled (0x62) */
1360 if (xscale
->trace
.buffer_enabled
)
1362 xscale_send_u32(target
, 0x62);
1363 xscale_send_u32(target
, 0x31);
1366 xscale_send_u32(target
, 0x30);
1369 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1370 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1372 for (i
= 7; i
>= 0; i
--)
1375 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1376 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1380 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1381 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1383 /* wait for and process debug entry */
1384 xscale_debug_entry(target
);
1386 LOG_DEBUG("disable single-step");
1387 xscale_disable_single_step(target
);
1389 LOG_DEBUG("set breakpoint at 0x%8.8x", breakpoint
->address
);
1390 xscale_set_breakpoint(target
, breakpoint
);
1394 /* enable any pending breakpoints and watchpoints */
1395 xscale_enable_breakpoints(target
);
1396 xscale_enable_watchpoints(target
);
1398 /* restore banked registers */
1399 xscale_restore_context(target
);
1401 /* send resume request (command 0x30 or 0x31)
1402 * clean the trace buffer if it is to be enabled (0x62) */
1403 if (xscale
->trace
.buffer_enabled
)
1405 xscale_send_u32(target
, 0x62);
1406 xscale_send_u32(target
, 0x31);
1409 xscale_send_u32(target
, 0x30);
1412 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1413 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1415 for (i
= 7; i
>= 0; i
--)
1418 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1419 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1423 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1424 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1426 target
->debug_reason
= DBG_REASON_NOTHALTED
;
1428 if (!debug_execution
)
1430 /* registers are now invalid */
1431 armv4_5_invalidate_core_regs(target
);
1432 target
->state
= TARGET_RUNNING
;
1433 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1437 target
->state
= TARGET_DEBUG_RUNNING
;
1438 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1441 LOG_DEBUG("target resumed");
1443 xscale
->handler_running
= 1;
1448 static int xscale_step_inner(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
)
1450 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1451 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1453 u32 current_pc
, next_pc
;
1458 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1460 /* calculate PC of next instruction */
1461 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1464 target_read_u32(target
, current_pc
, ¤t_opcode
);
1465 LOG_ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1469 LOG_DEBUG("enable single-step");
1470 if ((retval
=xscale_enable_single_step(target
, next_pc
))!=ERROR_OK
)
1473 /* restore banked registers */
1474 if ((retval
=xscale_restore_context(target
))!=ERROR_OK
)
1477 /* send resume request (command 0x30 or 0x31)
1478 * clean the trace buffer if it is to be enabled (0x62) */
1479 if (xscale
->trace
.buffer_enabled
)
1481 if ((retval
=xscale_send_u32(target
, 0x62))!=ERROR_OK
)
1483 if ((retval
=xscale_send_u32(target
, 0x31))!=ERROR_OK
)
1487 if ((retval
=xscale_send_u32(target
, 0x30))!=ERROR_OK
)
1491 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32)))!=ERROR_OK
)
1493 LOG_DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1495 for (i
= 7; i
>= 0; i
--)
1498 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32)))!=ERROR_OK
)
1500 LOG_DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1504 if ((retval
=xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32)))!=ERROR_OK
)
1506 LOG_DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1508 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1510 /* registers are now invalid */
1511 if ((retval
=armv4_5_invalidate_core_regs(target
))!=ERROR_OK
)
1514 /* wait for and process debug entry */
1515 if ((retval
=xscale_debug_entry(target
))!=ERROR_OK
)
1518 LOG_DEBUG("disable single-step");
1519 if ((retval
=xscale_disable_single_step(target
))!=ERROR_OK
)
1522 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1527 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
)
1529 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1530 breakpoint_t
*breakpoint
= target
->breakpoints
;
1535 if (target
->state
!= TARGET_HALTED
)
1537 LOG_WARNING("target not halted");
1538 return ERROR_TARGET_NOT_HALTED
;
1541 /* current = 1: continue on current pc, otherwise continue at <address> */
1543 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1545 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1547 /* if we're at the reset vector, we have to simulate the step */
1548 if (current_pc
== 0x0)
1550 if ((retval
=arm_simulate_step(target
, NULL
))!=ERROR_OK
)
1552 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1554 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1555 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1560 /* the front-end may request us not to handle breakpoints */
1561 if (handle_breakpoints
)
1562 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1564 if ((retval
=xscale_unset_breakpoint(target
, breakpoint
))!=ERROR_OK
)
1568 retval
= xscale_step_inner(target
, current
, address
, handle_breakpoints
);
1572 xscale_set_breakpoint(target
, breakpoint
);
1575 LOG_DEBUG("target stepped");
1581 int xscale_assert_reset(target_t
*target
)
1583 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1584 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1586 LOG_DEBUG("target->state: %s",
1587 Jim_Nvp_value2name_simple( nvp_target_state
, target
->state
)->name
);
1589 /* select DCSR instruction (set endstate to R-T-I to ensure we don't
1590 * end up in T-L-R, which would reset JTAG
1592 jtag_add_end_state(TAP_IDLE
);
1593 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, xscale
->jtag_info
.dcsr
);
1595 /* set Hold reset, Halt mode and Trap Reset */
1596 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1597 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1598 xscale_write_dcsr(target
, 1, 0);
1600 /* select BYPASS, because having DCSR selected caused problems on the PXA27x */
1601 xscale_jtag_set_instr(xscale
->jtag_info
.tap
, 0x7f);
1602 jtag_execute_queue();
1605 jtag_add_reset(0, 1);
1607 /* sleep 1ms, to be sure we fulfill any requirements */
1608 jtag_add_sleep(1000);
1609 jtag_execute_queue();
1611 target
->state
= TARGET_RESET
;
1613 if (target
->reset_halt
)
1616 if ((retval
= target_halt(target
))!=ERROR_OK
)
1623 int xscale_deassert_reset(target_t
*target
)
1625 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1626 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1628 fileio_t debug_handler
;
1636 breakpoint_t
*breakpoint
= target
->breakpoints
;
1640 xscale
->ibcr_available
= 2;
1641 xscale
->ibcr0_used
= 0;
1642 xscale
->ibcr1_used
= 0;
1644 xscale
->dbr_available
= 2;
1645 xscale
->dbr0_used
= 0;
1646 xscale
->dbr1_used
= 0;
1648 /* mark all hardware breakpoints as unset */
1651 if (breakpoint
->type
== BKPT_HARD
)
1653 breakpoint
->set
= 0;
1655 breakpoint
= breakpoint
->next
;
1658 if (!xscale
->handler_installed
)
1661 jtag_add_reset(0, 0);
1663 /* wait 300ms; 150 and 100ms were not enough */
1664 jtag_add_sleep(300*1000);
1666 jtag_add_runtest(2030, TAP_IDLE
);
1667 jtag_execute_queue();
1669 /* set Hold reset, Halt mode and Trap Reset */
1670 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1671 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1672 xscale_write_dcsr(target
, 1, 0);
1674 /* Load debug handler */
1675 if (fileio_open(&debug_handler
, "xscale/debug_handler.bin", FILEIO_READ
, FILEIO_BINARY
) != ERROR_OK
)
1680 if ((binary_size
= debug_handler
.size
) % 4)
1682 LOG_ERROR("debug_handler.bin: size not a multiple of 4");
1686 if (binary_size
> 0x800)
1688 LOG_ERROR("debug_handler.bin: larger than 2kb");
1692 binary_size
= CEIL(binary_size
, 32) * 32;
1694 address
= xscale
->handler_address
;
1695 while (binary_size
> 0)
1700 if ((retval
= fileio_read(&debug_handler
, 32, buffer
, &buf_cnt
)) != ERROR_OK
)
1705 for (i
= 0; i
< buf_cnt
; i
+= 4)
1707 /* convert LE buffer to host-endian u32 */
1708 cache_line
[i
/ 4] = le_to_h_u32(&buffer
[i
]);
1711 for (; buf_cnt
< 32; buf_cnt
+= 4)
1713 cache_line
[buf_cnt
/ 4] = 0xe1a08008;
1716 /* only load addresses other than the reset vectors */
1717 if ((address
% 0x400) != 0x0)
1719 xscale_load_ic(target
, 1, address
, cache_line
);
1723 binary_size
-= buf_cnt
;
1726 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
1727 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
1729 jtag_add_runtest(30, TAP_IDLE
);
1731 jtag_add_sleep(100000);
1733 /* set Hold reset, Halt mode and Trap Reset */
1734 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1735 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1736 xscale_write_dcsr(target
, 1, 0);
1738 /* clear Hold reset to let the target run (should enter debug handler) */
1739 xscale_write_dcsr(target
, 0, 1);
1740 target
->state
= TARGET_RUNNING
;
1742 if (!target
->reset_halt
)
1744 jtag_add_sleep(10000);
1746 /* we should have entered debug now */
1747 xscale_debug_entry(target
);
1748 target
->state
= TARGET_HALTED
;
1750 /* resume the target */
1751 xscale_resume(target
, 1, 0x0, 1, 0);
1754 fileio_close(&debug_handler
);
1758 jtag_add_reset(0, 0);
1764 int xscale_soft_reset_halt(struct target_s
*target
)
1769 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
)
1774 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
)
1780 int xscale_full_context(target_t
*target
)
1782 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1790 if (target
->state
!= TARGET_HALTED
)
1792 LOG_WARNING("target not halted");
1793 return ERROR_TARGET_NOT_HALTED
;
1796 buffer
= malloc(4 * 8);
1798 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1799 * we can't enter User mode on an XScale (unpredictable),
1800 * but User shares registers with SYS
1802 for(i
= 1; i
< 7; i
++)
1806 /* check if there are invalid registers in the current mode
1808 for (j
= 0; j
<= 16; j
++)
1810 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
== 0)
1818 /* request banked registers */
1819 xscale_send_u32(target
, 0x0);
1822 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1823 tmp_cpsr
|= 0xc0; /* I/F bits */
1825 /* send CPSR for desired mode */
1826 xscale_send_u32(target
, tmp_cpsr
);
1828 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1829 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1831 xscale_receive(target
, buffer
, 8);
1832 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1833 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1834 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).valid
= 1;
1838 xscale_receive(target
, buffer
, 7);
1841 /* move data from buffer to register cache */
1842 for (j
= 8; j
<= 14; j
++)
1844 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]);
1845 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1846 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
= 1;
1856 int xscale_restore_context(target_t
*target
)
1858 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1864 if (target
->state
!= TARGET_HALTED
)
1866 LOG_WARNING("target not halted");
1867 return ERROR_TARGET_NOT_HALTED
;
1870 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1871 * we can't enter User mode on an XScale (unpredictable),
1872 * but User shares registers with SYS
1874 for(i
= 1; i
< 7; i
++)
1878 /* check if there are invalid registers in the current mode
1880 for (j
= 8; j
<= 14; j
++)
1882 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
== 1)
1886 /* if not USR/SYS, check if the SPSR needs to be written */
1887 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1889 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
== 1)
1897 /* send banked registers */
1898 xscale_send_u32(target
, 0x1);
1901 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1902 tmp_cpsr
|= 0xc0; /* I/F bits */
1904 /* send CPSR for desired mode */
1905 xscale_send_u32(target
, tmp_cpsr
);
1907 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1908 for (j
= 8; j
<= 14; j
++)
1910 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, j
).value
, 0, 32));
1911 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1914 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1916 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32));
1917 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1925 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1927 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1928 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1933 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1935 if (target
->state
!= TARGET_HALTED
)
1937 LOG_WARNING("target not halted");
1938 return ERROR_TARGET_NOT_HALTED
;
1941 /* sanitize arguments */
1942 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1943 return ERROR_INVALID_ARGUMENTS
;
1945 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1946 return ERROR_TARGET_UNALIGNED_ACCESS
;
1948 /* send memory read request (command 0x1n, n: access size) */
1949 if ((retval
=xscale_send_u32(target
, 0x10 | size
))!=ERROR_OK
)
1952 /* send base address for read request */
1953 if ((retval
=xscale_send_u32(target
, address
))!=ERROR_OK
)
1956 /* send number of requested data words */
1957 if ((retval
=xscale_send_u32(target
, count
))!=ERROR_OK
)
1960 /* receive data from target (count times 32-bit words in host endianness) */
1961 buf32
= malloc(4 * count
);
1962 if ((retval
=xscale_receive(target
, buf32
, count
))!=ERROR_OK
)
1965 /* extract data from host-endian buffer into byte stream */
1966 for (i
= 0; i
< count
; i
++)
1971 target_buffer_set_u32(target
, buffer
, buf32
[i
]);
1975 target_buffer_set_u16(target
, buffer
, buf32
[i
] & 0xffff);
1979 *buffer
++ = buf32
[i
] & 0xff;
1982 LOG_ERROR("should never get here");
1989 /* examine DCSR, to see if Sticky Abort (SA) got set */
1990 if ((retval
=xscale_read_dcsr(target
))!=ERROR_OK
)
1992 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1995 if ((retval
=xscale_send_u32(target
, 0x60))!=ERROR_OK
)
1998 return ERROR_TARGET_DATA_ABORT
;
2004 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
2006 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2007 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2010 LOG_DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
2012 if (target
->state
!= TARGET_HALTED
)
2014 LOG_WARNING("target not halted");
2015 return ERROR_TARGET_NOT_HALTED
;
2018 /* sanitize arguments */
2019 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
2020 return ERROR_INVALID_ARGUMENTS
;
2022 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
2023 return ERROR_TARGET_UNALIGNED_ACCESS
;
2025 /* send memory write request (command 0x2n, n: access size) */
2026 if ((retval
=xscale_send_u32(target
, 0x20 | size
))!=ERROR_OK
)
2029 /* send base address for read request */
2030 if ((retval
=xscale_send_u32(target
, address
))!=ERROR_OK
)
2033 /* send number of requested data words to be written*/
2034 if ((retval
=xscale_send_u32(target
, count
))!=ERROR_OK
)
2037 /* extract data from host-endian buffer into byte stream */
2039 for (i
= 0; i
< count
; i
++)
2044 value
= target_buffer_get_u32(target
, buffer
);
2045 xscale_send_u32(target
, value
);
2049 value
= target_buffer_get_u16(target
, buffer
);
2050 xscale_send_u32(target
, value
);
2055 xscale_send_u32(target
, value
);
2059 LOG_ERROR("should never get here");
2064 if ((retval
=xscale_send(target
, buffer
, count
, size
))!=ERROR_OK
)
2067 /* examine DCSR, to see if Sticky Abort (SA) got set */
2068 if ((retval
=xscale_read_dcsr(target
))!=ERROR_OK
)
2070 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
2073 if ((retval
=xscale_send_u32(target
, 0x60))!=ERROR_OK
)
2076 return ERROR_TARGET_DATA_ABORT
;
2082 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
)
2084 return xscale_write_memory(target
, address
, 4, count
, buffer
);
2087 u32
xscale_get_ttb(target_t
*target
)
2089 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2090 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2093 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_TTB
]);
2094 ttb
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_TTB
].value
, 0, 32);
2099 void xscale_disable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2101 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2102 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2105 /* read cp15 control register */
2106 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2107 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2110 cp15_control
&= ~0x1U
;
2115 xscale_send_u32(target
, 0x50);
2116 xscale_send_u32(target
, xscale
->cache_clean_address
);
2118 /* invalidate DCache */
2119 xscale_send_u32(target
, 0x51);
2121 cp15_control
&= ~0x4U
;
2126 /* invalidate ICache */
2127 xscale_send_u32(target
, 0x52);
2128 cp15_control
&= ~0x1000U
;
2131 /* write new cp15 control register */
2132 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2134 /* execute cpwait to ensure outstanding operations complete */
2135 xscale_send_u32(target
, 0x53);
2138 void xscale_enable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2140 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2141 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2144 /* read cp15 control register */
2145 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2146 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2149 cp15_control
|= 0x1U
;
2152 cp15_control
|= 0x4U
;
2155 cp15_control
|= 0x1000U
;
2157 /* write new cp15 control register */
2158 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2160 /* execute cpwait to ensure outstanding operations complete */
2161 xscale_send_u32(target
, 0x53);
2164 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2167 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2168 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2170 if (target
->state
!= TARGET_HALTED
)
2172 LOG_WARNING("target not halted");
2173 return ERROR_TARGET_NOT_HALTED
;
2176 if (breakpoint
->set
)
2178 LOG_WARNING("breakpoint already set");
2182 if (breakpoint
->type
== BKPT_HARD
)
2184 u32 value
= breakpoint
->address
| 1;
2185 if (!xscale
->ibcr0_used
)
2187 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], value
);
2188 xscale
->ibcr0_used
= 1;
2189 breakpoint
->set
= 1; /* breakpoint set on first breakpoint register */
2191 else if (!xscale
->ibcr1_used
)
2193 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], value
);
2194 xscale
->ibcr1_used
= 1;
2195 breakpoint
->set
= 2; /* breakpoint set on second breakpoint register */
2199 LOG_ERROR("BUG: no hardware comparator available");
2203 else if (breakpoint
->type
== BKPT_SOFT
)
2205 if (breakpoint
->length
== 4)
2207 /* keep the original instruction in target endianness */
2208 if((retval
= target
->type
->read_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2212 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2213 if((retval
= target_write_u32(target
, breakpoint
->address
, xscale
->arm_bkpt
)) != ERROR_OK
)
2220 /* keep the original instruction in target endianness */
2221 if((retval
= target
->type
->read_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2225 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2226 if((retval
= target_write_u32(target
, breakpoint
->address
, xscale
->thumb_bkpt
)) != ERROR_OK
)
2231 breakpoint
->set
= 1;
2237 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2239 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2240 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2242 if (target
->state
!= TARGET_HALTED
)
2244 LOG_WARNING("target not halted");
2245 return ERROR_TARGET_NOT_HALTED
;
2248 if ((breakpoint
->type
== BKPT_HARD
) && (xscale
->ibcr_available
< 1))
2250 LOG_INFO("no breakpoint unit available for hardware breakpoint");
2251 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2254 if ((breakpoint
->length
!= 2) && (breakpoint
->length
!= 4))
2256 LOG_INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2257 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2260 if (breakpoint
->type
== BKPT_HARD
)
2262 xscale
->ibcr_available
--;
2268 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2271 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2272 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2274 if (target
->state
!= TARGET_HALTED
)
2276 LOG_WARNING("target not halted");
2277 return ERROR_TARGET_NOT_HALTED
;
2280 if (!breakpoint
->set
)
2282 LOG_WARNING("breakpoint not set");
2286 if (breakpoint
->type
== BKPT_HARD
)
2288 if (breakpoint
->set
== 1)
2290 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], 0x0);
2291 xscale
->ibcr0_used
= 0;
2293 else if (breakpoint
->set
== 2)
2295 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], 0x0);
2296 xscale
->ibcr1_used
= 0;
2298 breakpoint
->set
= 0;
2302 /* restore original instruction (kept in target endianness) */
2303 if (breakpoint
->length
== 4)
2305 if((retval
= target
->type
->write_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2312 if((retval
= target
->type
->write_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
)) != ERROR_OK
)
2317 breakpoint
->set
= 0;
2323 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2325 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2326 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2328 if (target
->state
!= TARGET_HALTED
)
2330 LOG_WARNING("target not halted");
2331 return ERROR_TARGET_NOT_HALTED
;
2334 if (breakpoint
->set
)
2336 xscale_unset_breakpoint(target
, breakpoint
);
2339 if (breakpoint
->type
== BKPT_HARD
)
2340 xscale
->ibcr_available
++;
2345 int xscale_set_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2347 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2348 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2350 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2351 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2353 if (target
->state
!= TARGET_HALTED
)
2355 LOG_WARNING("target not halted");
2356 return ERROR_TARGET_NOT_HALTED
;
2359 xscale_get_reg(dbcon
);
2361 switch (watchpoint
->rw
)
2373 LOG_ERROR("BUG: watchpoint->rw neither read, write nor access");
2376 if (!xscale
->dbr0_used
)
2378 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR0
], watchpoint
->address
);
2379 dbcon_value
|= enable
;
2380 xscale_set_reg_u32(dbcon
, dbcon_value
);
2381 watchpoint
->set
= 1;
2382 xscale
->dbr0_used
= 1;
2384 else if (!xscale
->dbr1_used
)
2386 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR1
], watchpoint
->address
);
2387 dbcon_value
|= enable
<< 2;
2388 xscale_set_reg_u32(dbcon
, dbcon_value
);
2389 watchpoint
->set
= 2;
2390 xscale
->dbr1_used
= 1;
2394 LOG_ERROR("BUG: no hardware comparator available");
2401 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2403 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2404 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2406 if (target
->state
!= TARGET_HALTED
)
2408 LOG_WARNING("target not halted");
2409 return ERROR_TARGET_NOT_HALTED
;
2412 if (xscale
->dbr_available
< 1)
2414 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2417 if ((watchpoint
->length
!= 1) && (watchpoint
->length
!= 2) && (watchpoint
->length
!= 4))
2419 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2422 xscale
->dbr_available
--;
2427 int xscale_unset_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2429 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2430 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2431 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2432 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2434 if (target
->state
!= TARGET_HALTED
)
2436 LOG_WARNING("target not halted");
2437 return ERROR_TARGET_NOT_HALTED
;
2440 if (!watchpoint
->set
)
2442 LOG_WARNING("breakpoint not set");
2446 if (watchpoint
->set
== 1)
2448 dbcon_value
&= ~0x3;
2449 xscale_set_reg_u32(dbcon
, dbcon_value
);
2450 xscale
->dbr0_used
= 0;
2452 else if (watchpoint
->set
== 2)
2454 dbcon_value
&= ~0xc;
2455 xscale_set_reg_u32(dbcon
, dbcon_value
);
2456 xscale
->dbr1_used
= 0;
2458 watchpoint
->set
= 0;
2463 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2465 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2466 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2468 if (target
->state
!= TARGET_HALTED
)
2470 LOG_WARNING("target not halted");
2471 return ERROR_TARGET_NOT_HALTED
;
2474 if (watchpoint
->set
)
2476 xscale_unset_watchpoint(target
, watchpoint
);
2479 xscale
->dbr_available
++;
2484 void xscale_enable_watchpoints(struct target_s
*target
)
2486 watchpoint_t
*watchpoint
= target
->watchpoints
;
2490 if (watchpoint
->set
== 0)
2491 xscale_set_watchpoint(target
, watchpoint
);
2492 watchpoint
= watchpoint
->next
;
2496 void xscale_enable_breakpoints(struct target_s
*target
)
2498 breakpoint_t
*breakpoint
= target
->breakpoints
;
2500 /* set any pending breakpoints */
2503 if (breakpoint
->set
== 0)
2504 xscale_set_breakpoint(target
, breakpoint
);
2505 breakpoint
= breakpoint
->next
;
2509 int xscale_get_reg(reg_t
*reg
)
2511 xscale_reg_t
*arch_info
= reg
->arch_info
;
2512 target_t
*target
= arch_info
->target
;
2513 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2514 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2516 /* DCSR, TX and RX are accessible via JTAG */
2517 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2519 return xscale_read_dcsr(arch_info
->target
);
2521 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2523 /* 1 = consume register content */
2524 return xscale_read_tx(arch_info
->target
, 1);
2526 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2528 /* can't read from RX register (host -> debug handler) */
2531 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2533 /* can't (explicitly) read from TXRXCTRL register */
2536 else /* Other DBG registers have to be transfered by the debug handler */
2538 /* send CP read request (command 0x40) */
2539 xscale_send_u32(target
, 0x40);
2541 /* send CP register number */
2542 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2544 /* read register value */
2545 xscale_read_tx(target
, 1);
2546 buf_cpy(xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
, reg
->value
, 32);
2555 int xscale_set_reg(reg_t
*reg
, u8
* buf
)
2557 xscale_reg_t
*arch_info
= reg
->arch_info
;
2558 target_t
*target
= arch_info
->target
;
2559 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2560 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2561 u32 value
= buf_get_u32(buf
, 0, 32);
2563 /* DCSR, TX and RX are accessible via JTAG */
2564 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2566 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32, value
);
2567 return xscale_write_dcsr(arch_info
->target
, -1, -1);
2569 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2571 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
2572 return xscale_write_rx(arch_info
->target
);
2574 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2576 /* can't write to TX register (debug-handler -> host) */
2579 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2581 /* can't (explicitly) write to TXRXCTRL register */
2584 else /* Other DBG registers have to be transfered by the debug handler */
2586 /* send CP write request (command 0x41) */
2587 xscale_send_u32(target
, 0x41);
2589 /* send CP register number */
2590 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2592 /* send CP register value */
2593 xscale_send_u32(target
, value
);
2594 buf_set_u32(reg
->value
, 0, 32, value
);
2600 /* convenience wrapper to access XScale specific registers */
2601 int xscale_set_reg_u32(reg_t
*reg
, u32 value
)
2605 buf_set_u32(buf
, 0, 32, value
);
2607 return xscale_set_reg(reg
, buf
);
2610 int xscale_write_dcsr_sw(target_t
*target
, u32 value
)
2612 /* get pointers to arch-specific information */
2613 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2614 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2615 reg_t
*dcsr
= &xscale
->reg_cache
->reg_list
[XSCALE_DCSR
];
2616 xscale_reg_t
*dcsr_arch_info
= dcsr
->arch_info
;
2618 /* send CP write request (command 0x41) */
2619 xscale_send_u32(target
, 0x41);
2621 /* send CP register number */
2622 xscale_send_u32(target
, dcsr_arch_info
->dbg_handler_number
);
2624 /* send CP register value */
2625 xscale_send_u32(target
, value
);
2626 buf_set_u32(dcsr
->value
, 0, 32, value
);
2631 int xscale_read_trace(target_t
*target
)
2633 /* get pointers to arch-specific information */
2634 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2635 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2636 xscale_trace_data_t
**trace_data_p
;
2638 /* 258 words from debug handler
2639 * 256 trace buffer entries
2640 * 2 checkpoint addresses
2642 u32 trace_buffer
[258];
2643 int is_address
[256];
2646 if (target
->state
!= TARGET_HALTED
)
2648 LOG_WARNING("target must be stopped to read trace data");
2649 return ERROR_TARGET_NOT_HALTED
;
2652 /* send read trace buffer command (command 0x61) */
2653 xscale_send_u32(target
, 0x61);
2655 /* receive trace buffer content */
2656 xscale_receive(target
, trace_buffer
, 258);
2658 /* parse buffer backwards to identify address entries */
2659 for (i
= 255; i
>= 0; i
--)
2662 if (((trace_buffer
[i
] & 0xf0) == 0x90) ||
2663 ((trace_buffer
[i
] & 0xf0) == 0xd0))
2666 is_address
[--i
] = 1;
2668 is_address
[--i
] = 1;
2670 is_address
[--i
] = 1;
2672 is_address
[--i
] = 1;
2677 /* search first non-zero entry */
2678 for (j
= 0; (j
< 256) && (trace_buffer
[j
] == 0) && (!is_address
[j
]); j
++)
2683 LOG_DEBUG("no trace data collected");
2684 return ERROR_XSCALE_NO_TRACE_DATA
;
2687 for (trace_data_p
= &xscale
->trace
.data
; *trace_data_p
; trace_data_p
= &(*trace_data_p
)->next
)
2690 *trace_data_p
= malloc(sizeof(xscale_trace_data_t
));
2691 (*trace_data_p
)->next
= NULL
;
2692 (*trace_data_p
)->chkpt0
= trace_buffer
[256];
2693 (*trace_data_p
)->chkpt1
= trace_buffer
[257];
2694 (*trace_data_p
)->last_instruction
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
2695 (*trace_data_p
)->entries
= malloc(sizeof(xscale_trace_entry_t
) * (256 - j
));
2696 (*trace_data_p
)->depth
= 256 - j
;
2698 for (i
= j
; i
< 256; i
++)
2700 (*trace_data_p
)->entries
[i
- j
].data
= trace_buffer
[i
];
2702 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_ADDRESS
;
2704 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_MESSAGE
;
2710 int xscale_read_instruction(target_t
*target
, arm_instruction_t
*instruction
)
2712 /* get pointers to arch-specific information */
2713 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2714 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2721 if (!xscale
->trace
.image
)
2722 return ERROR_TRACE_IMAGE_UNAVAILABLE
;
2724 /* search for the section the current instruction belongs to */
2725 for (i
= 0; i
< xscale
->trace
.image
->num_sections
; i
++)
2727 if ((xscale
->trace
.image
->sections
[i
].base_address
<= xscale
->trace
.current_pc
) &&
2728 (xscale
->trace
.image
->sections
[i
].base_address
+ xscale
->trace
.image
->sections
[i
].size
> xscale
->trace
.current_pc
))
2737 /* current instruction couldn't be found in the image */
2738 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2741 if (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
)
2744 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2745 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2746 4, buf
, &size_read
)) != ERROR_OK
)
2748 LOG_ERROR("error while reading instruction: %i", retval
);
2749 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2751 opcode
= target_buffer_get_u32(target
, buf
);
2752 arm_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2754 else if (xscale
->trace
.core_state
== ARMV4_5_STATE_THUMB
)
2757 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2758 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2759 2, buf
, &size_read
)) != ERROR_OK
)
2761 LOG_ERROR("error while reading instruction: %i", retval
);
2762 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2764 opcode
= target_buffer_get_u16(target
, buf
);
2765 thumb_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2769 LOG_ERROR("BUG: unknown core state encountered");
2776 int xscale_branch_address(xscale_trace_data_t
*trace_data
, int i
, u32
*target
)
2778 /* if there are less than four entries prior to the indirect branch message
2779 * we can't extract the address */
2785 *target
= (trace_data
->entries
[i
-1].data
) | (trace_data
->entries
[i
-2].data
<< 8) |
2786 (trace_data
->entries
[i
-3].data
<< 16) | (trace_data
->entries
[i
-4].data
<< 24);
2791 int xscale_analyze_trace(target_t
*target
, command_context_t
*cmd_ctx
)
2793 /* get pointers to arch-specific information */
2794 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2795 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2798 xscale_trace_data_t
*trace_data
= xscale
->trace
.data
;
2807 xscale
->trace
.core_state
= ARMV4_5_STATE_ARM
;
2812 for (i
= 0; i
< trace_data
->depth
; i
++)
2818 if (trace_data
->entries
[i
].type
== XSCALE_TRACE_ADDRESS
)
2821 switch ((trace_data
->entries
[i
].data
& 0xf0) >> 4)
2823 case 0: /* Exceptions */
2831 exception
= (trace_data
->entries
[i
].data
& 0x70) >> 4;
2833 next_pc
= (trace_data
->entries
[i
].data
& 0xf0) >> 2;
2834 command_print(cmd_ctx
, "--- exception %i ---", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2836 case 8: /* Direct Branch */
2839 case 9: /* Indirect Branch */
2841 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2846 case 13: /* Checkpointed Indirect Branch */
2847 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2850 if (((chkpt
== 0) && (next_pc
!= trace_data
->chkpt0
))
2851 || ((chkpt
== 1) && (next_pc
!= trace_data
->chkpt1
)))
2852 LOG_WARNING("checkpointed indirect branch target address doesn't match checkpoint");
2854 /* explicit fall-through */
2855 case 12: /* Checkpointed Direct Branch */
2860 next_pc
= trace_data
->chkpt0
;
2863 else if (chkpt
== 1)
2866 next_pc
= trace_data
->chkpt0
;
2871 LOG_WARNING("more than two checkpointed branches encountered");
2874 case 15: /* Roll-over */
2877 default: /* Reserved */
2878 command_print(cmd_ctx
, "--- reserved trace message ---");
2879 LOG_ERROR("BUG: trace message %i is reserved", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2883 if (xscale
->trace
.pc_ok
)
2885 int executed
= (trace_data
->entries
[i
].data
& 0xf) + rollover
* 16;
2886 arm_instruction_t instruction
;
2888 if ((exception
== 6) || (exception
== 7))
2890 /* IRQ or FIQ exception, no instruction executed */
2894 while (executed
-- >= 0)
2896 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2898 /* can't continue tracing with no image available */
2899 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2903 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2905 /* TODO: handle incomplete images */
2909 /* a precise abort on a load to the PC is included in the incremental
2910 * word count, other instructions causing data aborts are not included
2912 if ((executed
== 0) && (exception
== 4)
2913 && ((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDM
)))
2915 if ((instruction
.type
== ARM_LDM
)
2916 && ((instruction
.info
.load_store_multiple
.register_list
& 0x8000) == 0))
2920 else if (((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDRSH
))
2921 && (instruction
.info
.load_store
.Rd
!= 15))
2927 /* only the last instruction executed
2928 * (the one that caused the control flow change)
2929 * could be a taken branch
2931 if (((executed
== -1) && (branch
== 1)) &&
2932 (((instruction
.type
== ARM_B
) ||
2933 (instruction
.type
== ARM_BL
) ||
2934 (instruction
.type
== ARM_BLX
)) &&
2935 (instruction
.info
.b_bl_bx_blx
.target_address
!= -1)))
2937 xscale
->trace
.current_pc
= instruction
.info
.b_bl_bx_blx
.target_address
;
2941 xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2;
2943 command_print(cmd_ctx
, "%s", instruction
.text
);
2951 xscale
->trace
.current_pc
= next_pc
;
2952 xscale
->trace
.pc_ok
= 1;
2956 for (; xscale
->trace
.current_pc
< trace_data
->last_instruction
; xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2)
2958 arm_instruction_t instruction
;
2959 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2961 /* can't continue tracing with no image available */
2962 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2966 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2968 /* TODO: handle incomplete images */
2971 command_print(cmd_ctx
, "%s", instruction
.text
);
2974 trace_data
= trace_data
->next
;
2980 void xscale_build_reg_cache(target_t
*target
)
2982 /* get pointers to arch-specific information */
2983 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2984 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2986 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
2987 xscale_reg_t
*arch_info
= malloc(sizeof(xscale_reg_arch_info
));
2989 int num_regs
= sizeof(xscale_reg_arch_info
) / sizeof(xscale_reg_t
);
2991 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
2992 armv4_5
->core_cache
= (*cache_p
);
2994 /* register a register arch-type for XScale dbg registers only once */
2995 if (xscale_reg_arch_type
== -1)
2996 xscale_reg_arch_type
= register_reg_arch_type(xscale_get_reg
, xscale_set_reg
);
2998 (*cache_p
)->next
= malloc(sizeof(reg_cache_t
));
2999 cache_p
= &(*cache_p
)->next
;
3001 /* fill in values for the xscale reg cache */
3002 (*cache_p
)->name
= "XScale registers";
3003 (*cache_p
)->next
= NULL
;
3004 (*cache_p
)->reg_list
= malloc(num_regs
* sizeof(reg_t
));
3005 (*cache_p
)->num_regs
= num_regs
;
3007 for (i
= 0; i
< num_regs
; i
++)
3009 (*cache_p
)->reg_list
[i
].name
= xscale_reg_list
[i
];
3010 (*cache_p
)->reg_list
[i
].value
= calloc(4, 1);
3011 (*cache_p
)->reg_list
[i
].dirty
= 0;
3012 (*cache_p
)->reg_list
[i
].valid
= 0;
3013 (*cache_p
)->reg_list
[i
].size
= 32;
3014 (*cache_p
)->reg_list
[i
].bitfield_desc
= NULL
;
3015 (*cache_p
)->reg_list
[i
].num_bitfields
= 0;
3016 (*cache_p
)->reg_list
[i
].arch_info
= &arch_info
[i
];
3017 (*cache_p
)->reg_list
[i
].arch_type
= xscale_reg_arch_type
;
3018 arch_info
[i
] = xscale_reg_arch_info
[i
];
3019 arch_info
[i
].target
= target
;
3022 xscale
->reg_cache
= (*cache_p
);
3025 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
3030 int xscale_quit(void)
3035 int xscale_init_arch_info(target_t
*target
, xscale_common_t
*xscale
, jtag_tap_t
*tap
, const char *variant
)
3037 armv4_5_common_t
*armv4_5
;
3038 u32 high_reset_branch
, low_reset_branch
;
3041 armv4_5
= &xscale
->armv4_5_common
;
3043 /* store architecture specfic data (none so far) */
3044 xscale
->arch_info
= NULL
;
3045 xscale
->common_magic
= XSCALE_COMMON_MAGIC
;
3047 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
3048 xscale
->variant
= strdup(variant
);
3050 /* prepare JTAG information for the new target */
3051 xscale
->jtag_info
.tap
= tap
;
3053 xscale
->jtag_info
.dbgrx
= 0x02;
3054 xscale
->jtag_info
.dbgtx
= 0x10;
3055 xscale
->jtag_info
.dcsr
= 0x09;
3056 xscale
->jtag_info
.ldic
= 0x07;
3058 if ((strcmp(xscale
->variant
, "pxa250") == 0) ||
3059 (strcmp(xscale
->variant
, "pxa255") == 0) ||
3060 (strcmp(xscale
->variant
, "pxa26x") == 0))
3062 xscale
->jtag_info
.ir_length
= 5;
3064 else if ((strcmp(xscale
->variant
, "pxa27x") == 0) ||
3065 (strcmp(xscale
->variant
, "ixp42x") == 0) ||
3066 (strcmp(xscale
->variant
, "ixp45x") == 0) ||
3067 (strcmp(xscale
->variant
, "ixp46x") == 0))
3069 xscale
->jtag_info
.ir_length
= 7;
3072 /* the debug handler isn't installed (and thus not running) at this time */
3073 xscale
->handler_installed
= 0;
3074 xscale
->handler_running
= 0;
3075 xscale
->handler_address
= 0xfe000800;
3077 /* clear the vectors we keep locally for reference */
3078 memset(xscale
->low_vectors
, 0, sizeof(xscale
->low_vectors
));
3079 memset(xscale
->high_vectors
, 0, sizeof(xscale
->high_vectors
));
3081 /* no user-specified vectors have been configured yet */
3082 xscale
->static_low_vectors_set
= 0x0;
3083 xscale
->static_high_vectors_set
= 0x0;
3085 /* calculate branches to debug handler */
3086 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
3087 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
3089 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
3090 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
3092 for (i
= 1; i
<= 7; i
++)
3094 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3095 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3098 /* 64kB aligned region used for DCache cleaning */
3099 xscale
->cache_clean_address
= 0xfffe0000;
3101 xscale
->hold_rst
= 0;
3102 xscale
->external_debug_break
= 0;
3104 xscale
->ibcr_available
= 2;
3105 xscale
->ibcr0_used
= 0;
3106 xscale
->ibcr1_used
= 0;
3108 xscale
->dbr_available
= 2;
3109 xscale
->dbr0_used
= 0;
3110 xscale
->dbr1_used
= 0;
3112 xscale
->arm_bkpt
= ARMV5_BKPT(0x0);
3113 xscale
->thumb_bkpt
= ARMV5_T_BKPT(0x0) & 0xffff;
3115 xscale
->vector_catch
= 0x1;
3117 xscale
->trace
.capture_status
= TRACE_IDLE
;
3118 xscale
->trace
.data
= NULL
;
3119 xscale
->trace
.image
= NULL
;
3120 xscale
->trace
.buffer_enabled
= 0;
3121 xscale
->trace
.buffer_fill
= 0;
3123 /* prepare ARMv4/5 specific information */
3124 armv4_5
->arch_info
= xscale
;
3125 armv4_5
->read_core_reg
= xscale_read_core_reg
;
3126 armv4_5
->write_core_reg
= xscale_write_core_reg
;
3127 armv4_5
->full_context
= xscale_full_context
;
3129 armv4_5_init_arch_info(target
, armv4_5
);
3131 xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
= -1;
3132 xscale
->armv4_5_mmu
.get_ttb
= xscale_get_ttb
;
3133 xscale
->armv4_5_mmu
.read_memory
= xscale_read_memory
;
3134 xscale
->armv4_5_mmu
.write_memory
= xscale_write_memory
;
3135 xscale
->armv4_5_mmu
.disable_mmu_caches
= xscale_disable_mmu_caches
;
3136 xscale
->armv4_5_mmu
.enable_mmu_caches
= xscale_enable_mmu_caches
;
3137 xscale
->armv4_5_mmu
.has_tiny_pages
= 1;
3138 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3143 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
3144 int xscale_target_create(struct target_s
*target
, Jim_Interp
*interp
)
3146 xscale_common_t
*xscale
= calloc(1,sizeof(xscale_common_t
));
3148 xscale_init_arch_info(target
, xscale
, target
->tap
, target
->variant
);
3149 xscale_build_reg_cache(target
);
3154 int xscale_handle_debug_handler_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3156 target_t
*target
= NULL
;
3157 armv4_5_common_t
*armv4_5
;
3158 xscale_common_t
*xscale
;
3160 u32 handler_address
;
3164 LOG_ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
3168 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3170 LOG_ERROR("no target '%s' configured", args
[0]);
3174 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3179 handler_address
= strtoul(args
[1], NULL
, 0);
3181 if (((handler_address
>= 0x800) && (handler_address
<= 0x1fef800)) ||
3182 ((handler_address
>= 0xfe000800) && (handler_address
<= 0xfffff800)))
3184 xscale
->handler_address
= handler_address
;
3188 LOG_ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
3195 int xscale_handle_cache_clean_address_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3197 target_t
*target
= NULL
;
3198 armv4_5_common_t
*armv4_5
;
3199 xscale_common_t
*xscale
;
3201 u32 cache_clean_address
;
3205 return ERROR_COMMAND_SYNTAX_ERROR
;
3208 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3210 LOG_ERROR("no target '%s' configured", args
[0]);
3214 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3219 cache_clean_address
= strtoul(args
[1], NULL
, 0);
3221 if (cache_clean_address
& 0xffff)
3223 LOG_ERROR("xscale cache_clean_address <address> must be 64kb aligned");
3227 xscale
->cache_clean_address
= cache_clean_address
;
3233 int xscale_handle_cache_info_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3235 target_t
*target
= get_current_target(cmd_ctx
);
3236 armv4_5_common_t
*armv4_5
;
3237 xscale_common_t
*xscale
;
3239 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3244 return armv4_5_handle_cache_info_command(cmd_ctx
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
3247 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
)
3249 armv4_5_common_t
*armv4_5
;
3250 xscale_common_t
*xscale
;
3257 if ((retval
= xscale_get_arch_pointers(target
, &armv4_5
, &xscale
)) != ERROR_OK
)
3261 u32 ret
= armv4_5_mmu_translate_va(target
, &xscale
->armv4_5_mmu
, virtual, &type
, &cb
, &domain
, &ap
);
3270 static int xscale_mmu(struct target_s
*target
, int *enabled
)
3272 armv4_5_common_t
*armv4_5
= target
->arch_info
;
3273 xscale_common_t
*xscale
= armv4_5
->arch_info
;
3275 if (target
->state
!= TARGET_HALTED
)
3277 LOG_ERROR("Target not halted");
3278 return ERROR_TARGET_INVALID
;
3280 *enabled
= xscale
->armv4_5_mmu
.mmu_enabled
;
3284 int xscale_handle_mmu_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3286 target_t
*target
= get_current_target(cmd_ctx
);
3287 armv4_5_common_t
*armv4_5
;
3288 xscale_common_t
*xscale
;
3290 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3295 if (target
->state
!= TARGET_HALTED
)
3297 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3303 if (strcmp("enable", args
[0]) == 0)
3305 xscale_enable_mmu_caches(target
, 1, 0, 0);
3306 xscale
->armv4_5_mmu
.mmu_enabled
= 1;
3308 else if (strcmp("disable", args
[0]) == 0)
3310 xscale_disable_mmu_caches(target
, 1, 0, 0);
3311 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3315 command_print(cmd_ctx
, "mmu %s", (xscale
->armv4_5_mmu
.mmu_enabled
) ? "enabled" : "disabled");
3320 int xscale_handle_idcache_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3322 target_t
*target
= get_current_target(cmd_ctx
);
3323 armv4_5_common_t
*armv4_5
;
3324 xscale_common_t
*xscale
;
3325 int icache
= 0, dcache
= 0;
3327 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3332 if (target
->state
!= TARGET_HALTED
)
3334 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3338 if (strcmp(cmd
, "icache") == 0)
3340 else if (strcmp(cmd
, "dcache") == 0)
3345 if (strcmp("enable", args
[0]) == 0)
3347 xscale_enable_mmu_caches(target
, 0, dcache
, icache
);
3350 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 1;
3352 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 1;
3354 else if (strcmp("disable", args
[0]) == 0)
3356 xscale_disable_mmu_caches(target
, 0, dcache
, icache
);
3359 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 0;
3361 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 0;
3366 command_print(cmd_ctx
, "icache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
) ? "enabled" : "disabled");
3369 command_print(cmd_ctx
, "dcache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
) ? "enabled" : "disabled");
3374 int xscale_handle_vector_catch_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3376 target_t
*target
= get_current_target(cmd_ctx
);
3377 armv4_5_common_t
*armv4_5
;
3378 xscale_common_t
*xscale
;
3380 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3387 command_print(cmd_ctx
, "usage: xscale vector_catch [mask]");
3391 xscale
->vector_catch
= strtoul(args
[0], NULL
, 0);
3392 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 8, xscale
->vector_catch
);
3393 xscale_write_dcsr(target
, -1, -1);
3396 command_print(cmd_ctx
, "vector catch mask: 0x%2.2x", xscale
->vector_catch
);
3402 int xscale_handle_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3404 target_t
*target
= get_current_target(cmd_ctx
);
3405 armv4_5_common_t
*armv4_5
;
3406 xscale_common_t
*xscale
;
3409 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3414 if (target
->state
!= TARGET_HALTED
)
3416 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3420 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3422 xscale_trace_data_t
*td
, *next_td
;
3423 xscale
->trace
.buffer_enabled
= 1;
3425 /* free old trace data */
3426 td
= xscale
->trace
.data
;
3436 xscale
->trace
.data
= NULL
;
3438 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3440 xscale
->trace
.buffer_enabled
= 0;
3443 if ((argc
>= 2) && (strcmp("fill", args
[1]) == 0))
3446 xscale
->trace
.buffer_fill
= strtoul(args
[2], NULL
, 0);
3448 xscale
->trace
.buffer_fill
= 1;
3450 else if ((argc
>= 2) && (strcmp("wrap", args
[1]) == 0))
3452 xscale
->trace
.buffer_fill
= -1;
3455 if (xscale
->trace
.buffer_enabled
)
3457 /* if we enable the trace buffer in fill-once
3458 * mode we know the address of the first instruction */
3459 xscale
->trace
.pc_ok
= 1;
3460 xscale
->trace
.current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
3464 /* otherwise the address is unknown, and we have no known good PC */
3465 xscale
->trace
.pc_ok
= 0;
3468 command_print(cmd_ctx
, "trace buffer %s (%s)",
3469 (xscale
->trace
.buffer_enabled
) ? "enabled" : "disabled",
3470 (xscale
->trace
.buffer_fill
> 0) ? "fill" : "wrap");
3472 dcsr_value
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32);
3473 if (xscale
->trace
.buffer_fill
>= 0)
3474 xscale_write_dcsr_sw(target
, (dcsr_value
& 0xfffffffc) | 2);
3476 xscale_write_dcsr_sw(target
, dcsr_value
& 0xfffffffc);
3481 int xscale_handle_trace_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3484 armv4_5_common_t
*armv4_5
;
3485 xscale_common_t
*xscale
;
3489 command_print(cmd_ctx
, "usage: xscale trace_image <file> [base address] [type]");
3493 target
= get_current_target(cmd_ctx
);
3495 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3500 if (xscale
->trace
.image
)
3502 image_close(xscale
->trace
.image
);
3503 free(xscale
->trace
.image
);
3504 command_print(cmd_ctx
, "previously loaded image found and closed");
3507 xscale
->trace
.image
= malloc(sizeof(image_t
));
3508 xscale
->trace
.image
->base_address_set
= 0;
3509 xscale
->trace
.image
->start_address_set
= 0;
3511 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
3514 xscale
->trace
.image
->base_address_set
= 1;
3515 xscale
->trace
.image
->base_address
= strtoul(args
[1], NULL
, 0);
3519 xscale
->trace
.image
->base_address_set
= 0;
3522 if (image_open(xscale
->trace
.image
, args
[0], (argc
>= 3) ? args
[2] : NULL
) != ERROR_OK
)
3524 free(xscale
->trace
.image
);
3525 xscale
->trace
.image
= NULL
;
3532 int xscale_handle_dump_trace_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3534 target_t
*target
= get_current_target(cmd_ctx
);
3535 armv4_5_common_t
*armv4_5
;
3536 xscale_common_t
*xscale
;
3537 xscale_trace_data_t
*trace_data
;
3540 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3545 if (target
->state
!= TARGET_HALTED
)
3547 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3553 command_print(cmd_ctx
, "usage: xscale dump_trace <file>");
3557 trace_data
= xscale
->trace
.data
;
3561 command_print(cmd_ctx
, "no trace data collected");
3565 if (fileio_open(&file
, args
[0], FILEIO_WRITE
, FILEIO_BINARY
) != ERROR_OK
)
3574 fileio_write_u32(&file
, trace_data
->chkpt0
);
3575 fileio_write_u32(&file
, trace_data
->chkpt1
);
3576 fileio_write_u32(&file
, trace_data
->last_instruction
);
3577 fileio_write_u32(&file
, trace_data
->depth
);
3579 for (i
= 0; i
< trace_data
->depth
; i
++)
3580 fileio_write_u32(&file
, trace_data
->entries
[i
].data
| ((trace_data
->entries
[i
].type
& 0xffff) << 16));
3582 trace_data
= trace_data
->next
;
3585 fileio_close(&file
);
3590 int xscale_handle_analyze_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3592 target_t
*target
= get_current_target(cmd_ctx
);
3593 armv4_5_common_t
*armv4_5
;
3594 xscale_common_t
*xscale
;
3596 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3601 xscale_analyze_trace(target
, cmd_ctx
);
3606 int xscale_handle_cp15(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3608 target_t
*target
= get_current_target(cmd_ctx
);
3609 armv4_5_common_t
*armv4_5
;
3610 xscale_common_t
*xscale
;
3612 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3617 if (target
->state
!= TARGET_HALTED
)
3619 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3626 reg_no
= strtoul(args
[0], NULL
, 0);
3627 /*translate from xscale cp15 register no to openocd register*/
3631 reg_no
= XSCALE_MAINID
;
3634 reg_no
= XSCALE_CTRL
;
3637 reg_no
= XSCALE_TTB
;
3640 reg_no
= XSCALE_DAC
;
3643 reg_no
= XSCALE_FSR
;
3646 reg_no
= XSCALE_FAR
;
3649 reg_no
= XSCALE_PID
;
3652 reg_no
= XSCALE_CPACCESS
;
3655 command_print(cmd_ctx
, "invalid register number");
3656 return ERROR_INVALID_ARGUMENTS
;
3658 reg
= &xscale
->reg_cache
->reg_list
[reg_no
];
3665 /* read cp15 control register */
3666 xscale_get_reg(reg
);
3667 value
= buf_get_u32(reg
->value
, 0, 32);
3668 command_print(cmd_ctx
, "%s (/%i): 0x%x", reg
->name
, reg
->size
, value
);
3673 u32 value
= strtoul(args
[1], NULL
, 0);
3675 /* send CP write request (command 0x41) */
3676 xscale_send_u32(target
, 0x41);
3678 /* send CP register number */
3679 xscale_send_u32(target
, reg_no
);
3681 /* send CP register value */
3682 xscale_send_u32(target
, value
);
3684 /* execute cpwait to ensure outstanding operations complete */
3685 xscale_send_u32(target
, 0x53);
3689 command_print(cmd_ctx
, "usage: cp15 [register]<, [value]>");
3695 int xscale_register_commands(struct command_context_s
*cmd_ctx
)
3697 command_t
*xscale_cmd
;
3699 xscale_cmd
= register_command(cmd_ctx
, NULL
, "xscale", NULL
, COMMAND_ANY
, "xscale specific commands");
3701 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");
3702 register_command(cmd_ctx
, xscale_cmd
, "cache_clean_address", xscale_handle_cache_clean_address_command
, COMMAND_ANY
, NULL
);
3704 register_command(cmd_ctx
, xscale_cmd
, "cache_info", xscale_handle_cache_info_command
, COMMAND_EXEC
, NULL
);
3705 register_command(cmd_ctx
, xscale_cmd
, "mmu", xscale_handle_mmu_command
, COMMAND_EXEC
, "['enable'|'disable'] the MMU");
3706 register_command(cmd_ctx
, xscale_cmd
, "icache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the ICache");
3707 register_command(cmd_ctx
, xscale_cmd
, "dcache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the DCache");
3709 register_command(cmd_ctx
, xscale_cmd
, "vector_catch", xscale_handle_vector_catch_command
, COMMAND_EXEC
, "<mask> of vectors that should be catched");
3711 register_command(cmd_ctx
, xscale_cmd
, "trace_buffer", xscale_handle_trace_buffer_command
, COMMAND_EXEC
, "<enable|disable> ['fill' [n]|'wrap']");
3713 register_command(cmd_ctx
, xscale_cmd
, "dump_trace", xscale_handle_dump_trace_command
, COMMAND_EXEC
, "dump content of trace buffer to <file>");
3714 register_command(cmd_ctx
, xscale_cmd
, "analyze_trace", xscale_handle_analyze_trace_buffer_command
, COMMAND_EXEC
, "analyze content of trace buffer");
3715 register_command(cmd_ctx
, xscale_cmd
, "trace_image", xscale_handle_trace_image_command
,
3716 COMMAND_EXEC
, "load image from <file> [base address]");
3718 register_command(cmd_ctx
, xscale_cmd
, "cp15", xscale_handle_cp15
, COMMAND_EXEC
, "access coproc 15 <register> [value]");
3720 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)