1 /***************************************************************************
2 * Copyright (C) 2006, 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
24 #include "replacements.h"
31 #include "arm_simulator.h"
32 #include "arm_disassembler.h"
35 #include "binarybuffer.h"
36 #include "time_support.h"
37 #include "breakpoints.h"
43 #include <sys/types.h>
49 int xscale_register_commands(struct command_context_s
*cmd_ctx
);
51 /* forward declarations */
52 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
);
53 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
56 int xscale_arch_state(struct target_s
*target
);
57 int xscale_poll(target_t
*target
);
58 int xscale_halt(target_t
*target
);
59 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
);
60 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
);
61 int xscale_debug_entry(target_t
*target
);
62 int xscale_restore_context(target_t
*target
);
64 int xscale_assert_reset(target_t
*target
);
65 int xscale_deassert_reset(target_t
*target
);
66 int xscale_soft_reset_halt(struct target_s
*target
);
67 int xscale_prepare_reset_halt(struct target_s
*target
);
69 int xscale_set_reg_u32(reg_t
*reg
, u32 value
);
71 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
);
72 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
);
74 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
75 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
76 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
);
77 int xscale_checksum_memory(struct target_s
*target
, u32 address
, u32 count
, u32
* checksum
);
79 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
80 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
81 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
82 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
83 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
84 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
85 void xscale_enable_watchpoints(struct target_s
*target
);
86 void xscale_enable_breakpoints(struct target_s
*target
);
87 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
);
88 static int xscale_mmu(struct target_s
*target
, int *enabled
);
90 int xscale_read_trace(target_t
*target
);
92 target_type_t xscale_target
=
97 .arch_state
= xscale_arch_state
,
99 .target_request_data
= NULL
,
102 .resume
= xscale_resume
,
105 .assert_reset
= xscale_assert_reset
,
106 .deassert_reset
= xscale_deassert_reset
,
107 .soft_reset_halt
= xscale_soft_reset_halt
,
108 .prepare_reset_halt
= xscale_prepare_reset_halt
,
110 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
112 .read_memory
= xscale_read_memory
,
113 .write_memory
= xscale_write_memory
,
114 .bulk_write_memory
= xscale_bulk_write_memory
,
115 .checksum_memory
= xscale_checksum_memory
,
117 .run_algorithm
= armv4_5_run_algorithm
,
119 .add_breakpoint
= xscale_add_breakpoint
,
120 .remove_breakpoint
= xscale_remove_breakpoint
,
121 .add_watchpoint
= xscale_add_watchpoint
,
122 .remove_watchpoint
= xscale_remove_watchpoint
,
124 .register_commands
= xscale_register_commands
,
125 .target_command
= xscale_target_command
,
126 .init_target
= xscale_init_target
,
129 .virt2phys
= xscale_virt2phys
,
133 char* xscale_reg_list
[] =
135 "XSCALE_MAINID", /* 0 */
145 "XSCALE_IBCR0", /* 10 */
155 "XSCALE_RX", /* 20 */
159 xscale_reg_t xscale_reg_arch_info
[] =
161 {XSCALE_MAINID
, NULL
},
162 {XSCALE_CACHETYPE
, NULL
},
164 {XSCALE_AUXCTRL
, NULL
},
170 {XSCALE_CPACCESS
, NULL
},
171 {XSCALE_IBCR0
, NULL
},
172 {XSCALE_IBCR1
, NULL
},
175 {XSCALE_DBCON
, NULL
},
176 {XSCALE_TBREG
, NULL
},
177 {XSCALE_CHKPT0
, NULL
},
178 {XSCALE_CHKPT1
, NULL
},
179 {XSCALE_DCSR
, NULL
}, /* DCSR accessed via JTAG or SW */
180 {-1, NULL
}, /* TX accessed via JTAG */
181 {-1, NULL
}, /* RX accessed via JTAG */
182 {-1, NULL
}, /* TXRXCTRL implicit access via JTAG */
185 int xscale_reg_arch_type
= -1;
187 int xscale_get_reg(reg_t
*reg
);
188 int xscale_set_reg(reg_t
*reg
, u8
*buf
);
190 int xscale_get_arch_pointers(target_t
*target
, armv4_5_common_t
**armv4_5_p
, xscale_common_t
**xscale_p
)
192 armv4_5_common_t
*armv4_5
= target
->arch_info
;
193 xscale_common_t
*xscale
= armv4_5
->arch_info
;
195 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
197 ERROR("target isn't an XScale target");
201 if (xscale
->common_magic
!= XSCALE_COMMON_MAGIC
)
203 ERROR("target isn't an XScale target");
207 *armv4_5_p
= armv4_5
;
213 int xscale_jtag_set_instr(int chain_pos
, u32 new_instr
)
215 jtag_device_t
*device
= jtag_get_device(chain_pos
);
217 if (buf_get_u32(device
->cur_instr
, 0, device
->ir_length
) != new_instr
)
221 field
.device
= chain_pos
;
222 field
.num_bits
= device
->ir_length
;
223 field
.out_value
= calloc(CEIL(field
.num_bits
, 8), 1);
224 buf_set_u32(field
.out_value
, 0, field
.num_bits
, new_instr
);
225 field
.out_mask
= NULL
;
226 field
.in_value
= NULL
;
227 jtag_set_check_value(&field
, device
->expected
, device
->expected_mask
, NULL
);
229 jtag_add_ir_scan(1, &field
, -1, NULL
);
231 free(field
.out_value
);
237 int xscale_jtag_callback(enum jtag_event event
, void *priv
)
241 case JTAG_TRST_ASSERTED
:
243 case JTAG_TRST_RELEASED
:
245 case JTAG_SRST_ASSERTED
:
247 case JTAG_SRST_RELEASED
:
250 WARNING("unhandled JTAG event");
256 int xscale_read_dcsr(target_t
*target
)
258 armv4_5_common_t
*armv4_5
= target
->arch_info
;
259 xscale_common_t
*xscale
= armv4_5
->arch_info
;
263 scan_field_t fields
[3];
265 u8 field0_check_value
= 0x2;
266 u8 field0_check_mask
= 0x7;
268 u8 field2_check_value
= 0x0;
269 u8 field2_check_mask
= 0x1;
271 jtag_add_end_state(TAP_PD
);
272 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
274 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
275 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
277 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
278 fields
[0].num_bits
= 3;
279 fields
[0].out_value
= &field0
;
280 fields
[0].out_mask
= NULL
;
281 fields
[0].in_value
= NULL
;
282 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
284 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
285 fields
[1].num_bits
= 32;
286 fields
[1].out_value
= NULL
;
287 fields
[1].out_mask
= NULL
;
288 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
289 fields
[1].in_handler
= NULL
;
290 fields
[1].in_handler_priv
= NULL
;
291 fields
[1].in_check_value
= NULL
;
292 fields
[1].in_check_mask
= NULL
;
296 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
297 fields
[2].num_bits
= 1;
298 fields
[2].out_value
= &field2
;
299 fields
[2].out_mask
= NULL
;
300 fields
[2].in_value
= NULL
;
301 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
303 jtag_add_dr_scan(3, fields
, -1, NULL
);
305 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
307 ERROR("JTAG error while reading DCSR");
311 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
312 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
314 /* write the register with the value we just read
315 * on this second pass, only the first bit of field0 is guaranteed to be 0)
317 field0_check_mask
= 0x1;
318 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
319 fields
[1].in_value
= NULL
;
321 jtag_add_end_state(TAP_RTI
);
323 jtag_add_dr_scan(3, fields
, -1, NULL
);
328 int xscale_receive(target_t
*target
, u32
*buffer
, int num_words
)
330 int retval
= ERROR_OK
;
331 armv4_5_common_t
*armv4_5
= target
->arch_info
;
332 xscale_common_t
*xscale
= armv4_5
->arch_info
;
334 enum tap_state path
[3];
335 scan_field_t fields
[3];
337 u8
*field0
= malloc(num_words
* 1);
338 u8 field0_check_value
= 0x2;
339 u8 field0_check_mask
= 0x6;
340 u32
*field1
= malloc(num_words
* 4);
341 u8 field2_check_value
= 0x0;
342 u8 field2_check_mask
= 0x1;
344 int words_scheduled
= 0;
352 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
353 fields
[0].num_bits
= 3;
354 fields
[0].out_value
= NULL
;
355 fields
[0].out_mask
= NULL
;
356 /* fields[0].in_value = field0; */
357 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
359 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
360 fields
[1].num_bits
= 32;
361 fields
[1].out_value
= NULL
;
362 fields
[1].out_mask
= NULL
;
363 fields
[1].in_value
= NULL
;
364 fields
[1].in_handler
= NULL
;
365 fields
[1].in_handler_priv
= NULL
;
366 fields
[1].in_check_value
= NULL
;
367 fields
[1].in_check_mask
= NULL
;
371 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
372 fields
[2].num_bits
= 1;
373 fields
[2].out_value
= NULL
;
374 fields
[2].out_mask
= NULL
;
375 fields
[2].in_value
= NULL
;
376 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
378 jtag_add_end_state(TAP_RTI
);
379 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
380 jtag_add_runtest(1, -1);
382 /* repeat until all words have been collected */
384 while (words_done
< num_words
)
388 for (i
= words_done
; i
< num_words
; i
++)
390 fields
[0].in_value
= &field0
[i
];
391 fields
[1].in_handler
= buf_to_u32_handler
;
392 fields
[1].in_handler_priv
= (u8
*)&field1
[i
];
394 jtag_add_pathmove(3, path
);
395 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
399 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
401 ERROR("JTAG error while receiving data from debug handler");
405 /* examine results */
406 for (i
= words_done
; i
< num_words
; i
++)
408 if (!(field0
[0] & 1))
410 /* move backwards if necessary */
412 for (j
= i
; j
< num_words
- 1; j
++)
414 field0
[j
] = field0
[j
+1];
415 field1
[j
] = field1
[j
+1];
420 if (words_scheduled
== 0)
422 if (attempts
++ == 1000)
424 ERROR("Failed to receiving data from debug handler after 1000 attempts");
425 retval
= ERROR_JTAG_QUEUE_FAILED
;
430 words_done
+= words_scheduled
;
433 for (i
= 0; i
< num_words
; i
++)
434 *(buffer
++) = buf_get_u32((u8
*)&field1
[i
], 0, 32);
441 int xscale_read_tx(target_t
*target
, int consume
)
443 armv4_5_common_t
*armv4_5
= target
->arch_info
;
444 xscale_common_t
*xscale
= armv4_5
->arch_info
;
445 enum tap_state path
[3];
446 enum tap_state noconsume_path
[9];
449 struct timeval timeout
, now
;
451 scan_field_t fields
[3];
453 u8 field0_check_value
= 0x2;
454 u8 field0_check_mask
= 0x6;
455 u8 field2_check_value
= 0x0;
456 u8 field2_check_mask
= 0x1;
458 jtag_add_end_state(TAP_RTI
);
460 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
466 noconsume_path
[0] = TAP_SDS
;
467 noconsume_path
[1] = TAP_CD
;
468 noconsume_path
[2] = TAP_E1D
;
469 noconsume_path
[3] = TAP_PD
;
470 noconsume_path
[4] = TAP_E2D
;
471 noconsume_path
[5] = TAP_UD
;
472 noconsume_path
[6] = TAP_SDS
;
473 noconsume_path
[7] = TAP_CD
;
474 noconsume_path
[8] = TAP_SD
;
476 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
477 fields
[0].num_bits
= 3;
478 fields
[0].out_value
= NULL
;
479 fields
[0].out_mask
= NULL
;
480 fields
[0].in_value
= &field0_in
;
481 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
483 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
484 fields
[1].num_bits
= 32;
485 fields
[1].out_value
= NULL
;
486 fields
[1].out_mask
= NULL
;
487 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
;
488 fields
[1].in_handler
= NULL
;
489 fields
[1].in_handler_priv
= NULL
;
490 fields
[1].in_check_value
= NULL
;
491 fields
[1].in_check_mask
= NULL
;
495 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
496 fields
[2].num_bits
= 1;
497 fields
[2].out_value
= NULL
;
498 fields
[2].out_mask
= NULL
;
499 fields
[2].in_value
= NULL
;
500 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
502 gettimeofday(&timeout
, NULL
);
503 timeval_add_time(&timeout
, 5, 0);
507 /* if we want to consume the register content (i.e. clear TX_READY),
508 * we have to go straight from Capture-DR to Shift-DR
509 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
512 jtag_add_pathmove(3, path
);
514 jtag_add_pathmove(sizeof(noconsume_path
)/sizeof(*noconsume_path
), noconsume_path
);
516 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
518 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
520 ERROR("JTAG error while reading TX");
521 return ERROR_TARGET_TIMEOUT
;
524 gettimeofday(&now
, NULL
);
525 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
527 ERROR("time out reading TX register");
528 return ERROR_TARGET_TIMEOUT
;
530 } while ((!(field0_in
& 1)) && consume
);
532 if (!(field0_in
& 1))
533 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
538 int xscale_write_rx(target_t
*target
)
540 armv4_5_common_t
*armv4_5
= target
->arch_info
;
541 xscale_common_t
*xscale
= armv4_5
->arch_info
;
544 struct timeval timeout
, now
;
546 scan_field_t fields
[3];
549 u8 field0_check_value
= 0x2;
550 u8 field0_check_mask
= 0x6;
552 u8 field2_check_value
= 0x0;
553 u8 field2_check_mask
= 0x1;
555 jtag_add_end_state(TAP_RTI
);
557 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
559 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
560 fields
[0].num_bits
= 3;
561 fields
[0].out_value
= &field0_out
;
562 fields
[0].out_mask
= NULL
;
563 fields
[0].in_value
= &field0_in
;
564 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
566 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
567 fields
[1].num_bits
= 32;
568 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
;
569 fields
[1].out_mask
= NULL
;
570 fields
[1].in_value
= NULL
;
571 fields
[1].in_handler
= NULL
;
572 fields
[1].in_handler_priv
= NULL
;
573 fields
[1].in_check_value
= NULL
;
574 fields
[1].in_check_mask
= NULL
;
578 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
579 fields
[2].num_bits
= 1;
580 fields
[2].out_value
= &field2
;
581 fields
[2].out_mask
= NULL
;
582 fields
[2].in_value
= NULL
;
583 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
585 gettimeofday(&timeout
, NULL
);
586 timeval_add_time(&timeout
, 5, 0);
588 /* poll until rx_read is low */
592 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
594 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
596 ERROR("JTAG error while writing RX");
600 gettimeofday(&now
, NULL
);
601 if ((now
.tv_sec
> timeout
.tv_sec
) || ((now
.tv_sec
== timeout
.tv_sec
)&& (now
.tv_usec
> timeout
.tv_usec
)))
603 ERROR("time out writing RX register");
604 return ERROR_TARGET_TIMEOUT
;
606 } while (field0_in
& 1);
610 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
612 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
614 ERROR("JTAG error while writing RX");
621 /* send count elements of size byte to the debug handler */
622 int xscale_send(target_t
*target
, u8
*buffer
, int count
, int size
)
624 armv4_5_common_t
*armv4_5
= target
->arch_info
;
625 xscale_common_t
*xscale
= armv4_5
->arch_info
;
630 u8 output
[4] = {0, 0, 0, 0};
632 scan_field_t fields
[3];
634 u8 field0_check_value
= 0x2;
635 u8 field0_check_mask
= 0x6;
637 u8 field2_check_value
= 0x0;
638 u8 field2_check_mask
= 0x1;
640 jtag_add_end_state(TAP_RTI
);
642 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
644 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
645 fields
[0].num_bits
= 3;
646 fields
[0].out_value
= &field0_out
;
647 fields
[0].out_mask
= NULL
;
648 fields
[0].in_handler
= NULL
;
649 if (!xscale
->fast_memory_access
)
651 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
654 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
655 fields
[1].num_bits
= 32;
656 fields
[1].out_value
= output
;
657 fields
[1].out_mask
= NULL
;
658 fields
[1].in_value
= NULL
;
659 fields
[1].in_handler
= NULL
;
660 fields
[1].in_handler_priv
= NULL
;
661 fields
[1].in_check_value
= NULL
;
662 fields
[1].in_check_mask
= NULL
;
666 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
667 fields
[2].num_bits
= 1;
668 fields
[2].out_value
= &field2
;
669 fields
[2].out_mask
= NULL
;
670 fields
[2].in_value
= NULL
;
671 fields
[2].in_handler
= NULL
;
672 if (!xscale
->fast_memory_access
)
674 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
679 int endianness
= target
->endianness
;
680 while (done_count
++ < count
)
682 if (endianness
== TARGET_LITTLE_ENDIAN
)
695 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
701 while (done_count
++ < count
)
703 /* extract sized element from target-endian buffer, and put it
704 * into little-endian output buffer
709 buf_set_u32(output
, 0, 32, target_buffer_get_u16(target
, buffer
));
715 ERROR("BUG: size neither 4, 2 nor 1");
719 jtag_add_dr_scan(3, fields
, TAP_RTI
, NULL
);
725 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
727 ERROR("JTAG error while sending data to debug handler");
734 int xscale_send_u32(target_t
*target
, u32 value
)
736 armv4_5_common_t
*armv4_5
= target
->arch_info
;
737 xscale_common_t
*xscale
= armv4_5
->arch_info
;
739 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
740 return xscale_write_rx(target
);
743 int xscale_write_dcsr(target_t
*target
, int hold_rst
, int ext_dbg_brk
)
745 armv4_5_common_t
*armv4_5
= target
->arch_info
;
746 xscale_common_t
*xscale
= armv4_5
->arch_info
;
750 scan_field_t fields
[3];
752 u8 field0_check_value
= 0x2;
753 u8 field0_check_mask
= 0x7;
755 u8 field2_check_value
= 0x0;
756 u8 field2_check_mask
= 0x1;
759 xscale
->hold_rst
= hold_rst
;
761 if (ext_dbg_brk
!= -1)
762 xscale
->external_debug_break
= ext_dbg_brk
;
764 jtag_add_end_state(TAP_RTI
);
765 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
767 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
768 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
770 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
771 fields
[0].num_bits
= 3;
772 fields
[0].out_value
= &field0
;
773 fields
[0].out_mask
= NULL
;
774 fields
[0].in_value
= NULL
;
775 jtag_set_check_value(fields
+0, &field0_check_value
, &field0_check_mask
, NULL
);
777 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
778 fields
[1].num_bits
= 32;
779 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
780 fields
[1].out_mask
= NULL
;
781 fields
[1].in_value
= NULL
;
782 fields
[1].in_handler
= NULL
;
783 fields
[1].in_handler_priv
= NULL
;
784 fields
[1].in_check_value
= NULL
;
785 fields
[1].in_check_mask
= NULL
;
789 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
790 fields
[2].num_bits
= 1;
791 fields
[2].out_value
= &field2
;
792 fields
[2].out_mask
= NULL
;
793 fields
[2].in_value
= NULL
;
794 jtag_set_check_value(fields
+2, &field2_check_value
, &field2_check_mask
, NULL
);
796 jtag_add_dr_scan(3, fields
, -1, NULL
);
798 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
800 ERROR("JTAG error while writing DCSR");
804 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
805 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
810 /* parity of the number of bits 0 if even; 1 if odd. for 32 bit words */
811 unsigned int parity (unsigned int v
)
818 DEBUG("parity of 0x%x is %i", ov
, (0x6996 >> v
) & 1);
819 return (0x6996 >> v
) & 1;
822 int xscale_load_ic(target_t
*target
, int mini
, u32 va
, u32 buffer
[8])
824 armv4_5_common_t
*armv4_5
= target
->arch_info
;
825 xscale_common_t
*xscale
= armv4_5
->arch_info
;
830 scan_field_t fields
[2];
832 DEBUG("loading miniIC at 0x%8.8x", va
);
834 jtag_add_end_state(TAP_RTI
);
835 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
837 /* CMD is b010 for Main IC and b011 for Mini IC */
839 buf_set_u32(&cmd
, 0, 3, 0x3);
841 buf_set_u32(&cmd
, 0, 3, 0x2);
843 buf_set_u32(&cmd
, 3, 3, 0x0);
845 /* virtual address of desired cache line */
846 buf_set_u32(packet
, 0, 27, va
>> 5);
848 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
849 fields
[0].num_bits
= 6;
850 fields
[0].out_value
= &cmd
;
851 fields
[0].out_mask
= NULL
;
852 fields
[0].in_value
= NULL
;
853 fields
[0].in_check_value
= NULL
;
854 fields
[0].in_check_mask
= NULL
;
855 fields
[0].in_handler
= NULL
;
856 fields
[0].in_handler_priv
= NULL
;
858 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
859 fields
[1].num_bits
= 27;
860 fields
[1].out_value
= packet
;
861 fields
[1].out_mask
= NULL
;
862 fields
[1].in_value
= NULL
;
863 fields
[1].in_check_value
= NULL
;
864 fields
[1].in_check_mask
= NULL
;
865 fields
[1].in_handler
= NULL
;
866 fields
[1].in_handler_priv
= NULL
;
868 jtag_add_dr_scan(2, fields
, -1, NULL
);
870 fields
[0].num_bits
= 32;
871 fields
[0].out_value
= packet
;
873 fields
[1].num_bits
= 1;
874 fields
[1].out_value
= &cmd
;
876 for (word
= 0; word
< 8; word
++)
878 buf_set_u32(packet
, 0, 32, buffer
[word
]);
879 cmd
= parity(*((u32
*)packet
));
880 jtag_add_dr_scan(2, fields
, -1, NULL
);
883 jtag_execute_queue();
888 int xscale_invalidate_ic_line(target_t
*target
, u32 va
)
890 armv4_5_common_t
*armv4_5
= target
->arch_info
;
891 xscale_common_t
*xscale
= armv4_5
->arch_info
;
895 scan_field_t fields
[2];
897 jtag_add_end_state(TAP_RTI
);
898 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
900 /* CMD for invalidate IC line b000, bits [6:4] b000 */
901 buf_set_u32(&cmd
, 0, 6, 0x0);
903 /* virtual address of desired cache line */
904 buf_set_u32(packet
, 0, 27, va
>> 5);
906 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
907 fields
[0].num_bits
= 6;
908 fields
[0].out_value
= &cmd
;
909 fields
[0].out_mask
= NULL
;
910 fields
[0].in_value
= NULL
;
911 fields
[0].in_check_value
= NULL
;
912 fields
[0].in_check_mask
= NULL
;
913 fields
[0].in_handler
= NULL
;
914 fields
[0].in_handler_priv
= NULL
;
916 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
917 fields
[1].num_bits
= 27;
918 fields
[1].out_value
= packet
;
919 fields
[1].out_mask
= NULL
;
920 fields
[1].in_value
= NULL
;
921 fields
[1].in_check_value
= NULL
;
922 fields
[1].in_check_mask
= NULL
;
923 fields
[1].in_handler
= NULL
;
924 fields
[1].in_handler_priv
= NULL
;
926 jtag_add_dr_scan(2, fields
, -1, NULL
);
931 int xscale_update_vectors(target_t
*target
)
933 armv4_5_common_t
*armv4_5
= target
->arch_info
;
934 xscale_common_t
*xscale
= armv4_5
->arch_info
;
937 u32 low_reset_branch
, high_reset_branch
;
939 for (i
= 1; i
< 8; i
++)
941 /* if there's a static vector specified for this exception, override */
942 if (xscale
->static_high_vectors_set
& (1 << i
))
944 xscale
->high_vectors
[i
] = xscale
->static_high_vectors
[i
];
948 if (target_read_u32(target
, 0xffff0000 + 4*i
, &xscale
->high_vectors
[i
]) != ERROR_OK
)
950 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
955 for (i
= 1; i
< 8; i
++)
957 if (xscale
->static_low_vectors_set
& (1 << i
))
959 xscale
->low_vectors
[i
] = xscale
->static_low_vectors
[i
];
963 if (target_read_u32(target
, 0x0 + 4*i
, &xscale
->low_vectors
[i
]) != ERROR_OK
)
965 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
970 /* calculate branches to debug handler */
971 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
972 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
974 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
975 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
977 /* invalidate and load exception vectors in mini i-cache */
978 xscale_invalidate_ic_line(target
, 0x0);
979 xscale_invalidate_ic_line(target
, 0xffff0000);
981 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
982 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
987 int xscale_arch_state(struct target_s
*target
)
989 armv4_5_common_t
*armv4_5
= target
->arch_info
;
990 xscale_common_t
*xscale
= armv4_5
->arch_info
;
994 "disabled", "enabled"
997 char *arch_dbg_reason
[] =
999 "", "\n(processor reset)", "\n(trace buffer full)"
1002 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
1004 ERROR("BUG: called for a non-ARMv4/5 target");
1008 USER("target halted in %s state due to %s, current mode: %s\n"
1009 "cpsr: 0x%8.8x pc: 0x%8.8x\n"
1010 "MMU: %s, D-Cache: %s, I-Cache: %s"
1012 armv4_5_state_strings
[armv4_5
->core_state
],
1013 target_debug_reason_strings
[target
->debug_reason
],
1014 armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)],
1015 buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32),
1016 buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32),
1017 state
[xscale
->armv4_5_mmu
.mmu_enabled
],
1018 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
],
1019 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
],
1020 arch_dbg_reason
[xscale
->arch_debug_reason
]);
1025 int xscale_poll(target_t
*target
)
1027 int retval
=ERROR_OK
;
1028 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1029 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1031 if ((target
->state
== TARGET_RUNNING
) || (target
->state
== TARGET_DEBUG_RUNNING
))
1033 enum target_state previous_state
= target
->state
;
1034 if ((retval
= xscale_read_tx(target
, 0)) == ERROR_OK
)
1037 /* there's data to read from the tx register, we entered debug state */
1038 xscale
->handler_running
= 1;
1040 target
->state
= TARGET_HALTED
;
1042 /* process debug entry, fetching current mode regs */
1043 retval
= xscale_debug_entry(target
);
1045 else if (retval
!= ERROR_TARGET_RESOURCE_NOT_AVAILABLE
)
1047 USER("error while polling TX register, reset CPU");
1048 /* here we "lie" so GDB won't get stuck and a reset can be perfomed */
1049 target
->state
= TARGET_HALTED
;
1052 /* debug_entry could have overwritten target state (i.e. immediate resume)
1053 * don't signal event handlers in that case
1055 if (target
->state
!= TARGET_HALTED
)
1058 /* if target was running, signal that we halted
1059 * otherwise we reentered from debug execution */
1060 if (previous_state
== TARGET_RUNNING
)
1061 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1063 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_HALTED
);
1068 int xscale_debug_entry(target_t
*target
)
1070 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1071 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1078 /* clear external dbg break (will be written on next DCSR read) */
1079 xscale
->external_debug_break
= 0;
1080 xscale_read_dcsr(target
);
1082 /* get r0, pc, r1 to r7 and cpsr */
1083 xscale_receive(target
, buffer
, 10);
1085 /* move r0 from buffer to register cache */
1086 buf_set_u32(armv4_5
->core_cache
->reg_list
[0].value
, 0, 32, buffer
[0]);
1087 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1088 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1089 DEBUG("r0: 0x%8.8x", buffer
[0]);
1091 /* move pc from buffer to register cache */
1092 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, buffer
[1]);
1093 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1094 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1095 DEBUG("pc: 0x%8.8x", buffer
[1]);
1097 /* move data from buffer to register cache */
1098 for (i
= 1; i
<= 7; i
++)
1100 buf_set_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32, buffer
[1 + i
]);
1101 armv4_5
->core_cache
->reg_list
[i
].dirty
= 1;
1102 armv4_5
->core_cache
->reg_list
[i
].valid
= 1;
1103 DEBUG("r%i: 0x%8.8x", i
, buffer
[i
+ 1]);
1106 buf_set_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32, buffer
[9]);
1107 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].dirty
= 1;
1108 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].valid
= 1;
1109 DEBUG("cpsr: 0x%8.8x", buffer
[9]);
1111 armv4_5
->core_mode
= buffer
[9] & 0x1f;
1112 if (armv4_5_mode_to_number(armv4_5
->core_mode
) == -1)
1114 target
->state
= TARGET_UNKNOWN
;
1115 ERROR("cpsr contains invalid mode value - communication failure");
1116 return ERROR_TARGET_FAILURE
;
1118 DEBUG("target entered debug state in %s mode", armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)]);
1120 if (buffer
[9] & 0x20)
1121 armv4_5
->core_state
= ARMV4_5_STATE_THUMB
;
1123 armv4_5
->core_state
= ARMV4_5_STATE_ARM
;
1125 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1126 if ((armv4_5
->core_mode
!= ARMV4_5_MODE_USR
) && (armv4_5
->core_mode
!= ARMV4_5_MODE_SYS
))
1128 xscale_receive(target
, buffer
, 8);
1129 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1130 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).dirty
= 0;
1131 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).valid
= 1;
1135 /* r8 to r14, but no spsr */
1136 xscale_receive(target
, buffer
, 7);
1139 /* move data from buffer to register cache */
1140 for (i
= 8; i
<= 14; i
++)
1142 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).value
, 0, 32, buffer
[i
- 8]);
1143 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).dirty
= 0;
1144 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).valid
= 1;
1147 /* examine debug reason */
1148 xscale_read_dcsr(target
);
1149 moe
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 2, 3);
1151 /* stored PC (for calculating fixup) */
1152 pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1156 case 0x0: /* Processor reset */
1157 target
->debug_reason
= DBG_REASON_DBGRQ
;
1158 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_RESET
;
1161 case 0x1: /* Instruction breakpoint hit */
1162 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1163 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1166 case 0x2: /* Data breakpoint hit */
1167 target
->debug_reason
= DBG_REASON_WATCHPOINT
;
1168 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1171 case 0x3: /* BKPT instruction executed */
1172 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1173 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1176 case 0x4: /* Ext. debug event */
1177 target
->debug_reason
= DBG_REASON_DBGRQ
;
1178 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1181 case 0x5: /* Vector trap occured */
1182 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1183 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1186 case 0x6: /* Trace buffer full break */
1187 target
->debug_reason
= DBG_REASON_DBGRQ
;
1188 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_TB_FULL
;
1191 case 0x7: /* Reserved */
1193 ERROR("Method of Entry is 'Reserved'");
1198 /* apply PC fixup */
1199 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, pc
);
1201 /* on the first debug entry, identify cache type */
1202 if (xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
== -1)
1206 /* read cp15 cache type register */
1207 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
]);
1208 cache_type_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
].value
, 0, 32);
1210 armv4_5_identify_cache(cache_type_reg
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
1213 /* examine MMU and Cache settings */
1214 /* read cp15 control register */
1215 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
1216 xscale
->cp15_control_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
1217 xscale
->armv4_5_mmu
.mmu_enabled
= (xscale
->cp15_control_reg
& 0x1U
) ? 1 : 0;
1218 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= (xscale
->cp15_control_reg
& 0x4U
) ? 1 : 0;
1219 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= (xscale
->cp15_control_reg
& 0x1000U
) ? 1 : 0;
1221 /* tracing enabled, read collected trace data */
1222 if (xscale
->trace
.buffer_enabled
)
1224 xscale_read_trace(target
);
1225 xscale
->trace
.buffer_fill
--;
1227 /* resume if we're still collecting trace data */
1228 if ((xscale
->arch_debug_reason
== XSCALE_DBG_REASON_TB_FULL
)
1229 && (xscale
->trace
.buffer_fill
> 0))
1231 xscale_resume(target
, 1, 0x0, 1, 0);
1235 xscale
->trace
.buffer_enabled
= 0;
1242 int xscale_halt(target_t
*target
)
1244 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1245 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1247 DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1249 if (target
->state
== TARGET_HALTED
)
1251 WARNING("target was already halted");
1252 return ERROR_TARGET_ALREADY_HALTED
;
1254 else if (target
->state
== TARGET_UNKNOWN
)
1256 /* this must not happen for a xscale target */
1257 ERROR("target was in unknown state when halt was requested");
1258 return ERROR_TARGET_INVALID
;
1260 else if (target
->state
== TARGET_RESET
)
1262 DEBUG("target->state == TARGET_RESET");
1266 /* assert external dbg break */
1267 xscale
->external_debug_break
= 1;
1268 xscale_read_dcsr(target
);
1270 target
->debug_reason
= DBG_REASON_DBGRQ
;
1276 int xscale_enable_single_step(struct target_s
*target
, u32 next_pc
)
1278 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1279 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1280 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1282 if (xscale
->ibcr0_used
)
1284 breakpoint_t
*ibcr0_bp
= breakpoint_find(target
, buf_get_u32(ibcr0
->value
, 0, 32) & 0xfffffffe);
1288 xscale_unset_breakpoint(target
, ibcr0_bp
);
1292 ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1297 xscale_set_reg_u32(ibcr0
, next_pc
| 0x1);
1302 int xscale_disable_single_step(struct target_s
*target
)
1304 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1305 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1306 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1308 xscale_set_reg_u32(ibcr0
, 0x0);
1313 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
)
1315 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1316 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1317 breakpoint_t
*breakpoint
= target
->breakpoints
;
1326 if (target
->state
!= TARGET_HALTED
)
1328 WARNING("target not halted");
1329 return ERROR_TARGET_NOT_HALTED
;
1332 if (!debug_execution
)
1334 target_free_all_working_areas(target
);
1337 /* update vector tables */
1338 xscale_update_vectors(target
);
1340 /* current = 1: continue on current pc, otherwise continue at <address> */
1342 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1344 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1346 /* if we're at the reset vector, we have to simulate the branch */
1347 if (current_pc
== 0x0)
1349 arm_simulate_step(target
, NULL
);
1350 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1353 /* the front-end may request us not to handle breakpoints */
1354 if (handle_breakpoints
)
1356 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1360 /* there's a breakpoint at the current PC, we have to step over it */
1361 DEBUG("unset breakpoint at 0x%8.8x", breakpoint
->address
);
1362 xscale_unset_breakpoint(target
, breakpoint
);
1364 /* calculate PC of next instruction */
1365 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1368 target_read_u32(target
, current_pc
, ¤t_opcode
);
1369 ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1372 DEBUG("enable single-step");
1373 xscale_enable_single_step(target
, next_pc
);
1375 /* restore banked registers */
1376 xscale_restore_context(target
);
1378 /* send resume request (command 0x30 or 0x31)
1379 * clean the trace buffer if it is to be enabled (0x62) */
1380 if (xscale
->trace
.buffer_enabled
)
1382 xscale_send_u32(target
, 0x62);
1383 xscale_send_u32(target
, 0x31);
1386 xscale_send_u32(target
, 0x30);
1389 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1390 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1392 for (i
= 7; i
>= 0; i
--)
1395 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1396 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1400 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1401 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1403 /* wait for and process debug entry */
1404 xscale_debug_entry(target
);
1406 DEBUG("disable single-step");
1407 xscale_disable_single_step(target
);
1409 DEBUG("set breakpoint at 0x%8.8x", breakpoint
->address
);
1410 xscale_set_breakpoint(target
, breakpoint
);
1414 /* enable any pending breakpoints and watchpoints */
1415 xscale_enable_breakpoints(target
);
1416 xscale_enable_watchpoints(target
);
1418 /* restore banked registers */
1419 xscale_restore_context(target
);
1421 /* send resume request (command 0x30 or 0x31)
1422 * clean the trace buffer if it is to be enabled (0x62) */
1423 if (xscale
->trace
.buffer_enabled
)
1425 xscale_send_u32(target
, 0x62);
1426 xscale_send_u32(target
, 0x31);
1429 xscale_send_u32(target
, 0x30);
1432 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1433 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1435 for (i
= 7; i
>= 0; i
--)
1438 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1439 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1443 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1444 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1446 target
->debug_reason
= DBG_REASON_NOTHALTED
;
1448 if (!debug_execution
)
1450 /* registers are now invalid */
1451 armv4_5_invalidate_core_regs(target
);
1452 target
->state
= TARGET_RUNNING
;
1453 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1457 target
->state
= TARGET_DEBUG_RUNNING
;
1458 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1461 DEBUG("target resumed");
1463 xscale
->handler_running
= 1;
1468 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
)
1470 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1471 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1472 breakpoint_t
*breakpoint
= target
->breakpoints
;
1474 u32 current_pc
, next_pc
;
1478 if (target
->state
!= TARGET_HALTED
)
1480 WARNING("target not halted");
1481 return ERROR_TARGET_NOT_HALTED
;
1484 /* current = 1: continue on current pc, otherwise continue at <address> */
1486 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1488 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1490 /* if we're at the reset vector, we have to simulate the step */
1491 if (current_pc
== 0x0)
1493 arm_simulate_step(target
, NULL
);
1494 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1496 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1497 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1502 /* the front-end may request us not to handle breakpoints */
1503 if (handle_breakpoints
)
1504 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1506 xscale_unset_breakpoint(target
, breakpoint
);
1509 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1511 /* calculate PC of next instruction */
1512 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1515 target_read_u32(target
, current_pc
, ¤t_opcode
);
1516 ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1519 DEBUG("enable single-step");
1520 xscale_enable_single_step(target
, next_pc
);
1522 /* restore banked registers */
1523 xscale_restore_context(target
);
1525 /* send resume request (command 0x30 or 0x31)
1526 * clean the trace buffer if it is to be enabled (0x62) */
1527 if (xscale
->trace
.buffer_enabled
)
1529 xscale_send_u32(target
, 0x62);
1530 xscale_send_u32(target
, 0x31);
1533 xscale_send_u32(target
, 0x30);
1536 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1537 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1539 for (i
= 7; i
>= 0; i
--)
1542 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1543 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1547 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1548 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1550 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1552 /* registers are now invalid */
1553 armv4_5_invalidate_core_regs(target
);
1555 /* wait for and process debug entry */
1556 xscale_debug_entry(target
);
1558 DEBUG("disable single-step");
1559 xscale_disable_single_step(target
);
1561 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1565 xscale_set_breakpoint(target
, breakpoint
);
1568 DEBUG("target stepped");
1574 int xscale_assert_reset(target_t
*target
)
1576 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1577 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1579 DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1581 /* select DCSR instruction (set endstate to R-T-I to ensure we don't
1582 * end up in T-L-R, which would reset JTAG
1584 jtag_add_end_state(TAP_RTI
);
1585 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
1587 /* set Hold reset, Halt mode and Trap Reset */
1588 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1589 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1590 xscale_write_dcsr(target
, 1, 0);
1592 /* select BYPASS, because having DCSR selected caused problems on the PXA27x */
1593 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, 0x7f);
1594 jtag_execute_queue();
1597 jtag_add_reset(0, 1);
1599 /* sleep 1ms, to be sure we fulfill any requirements */
1600 jtag_add_sleep(1000);
1601 jtag_execute_queue();
1603 target
->state
= TARGET_RESET
;
1608 int xscale_deassert_reset(target_t
*target
)
1610 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1611 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1613 fileio_t debug_handler
;
1621 breakpoint_t
*breakpoint
= target
->breakpoints
;
1625 xscale
->ibcr_available
= 2;
1626 xscale
->ibcr0_used
= 0;
1627 xscale
->ibcr1_used
= 0;
1629 xscale
->dbr_available
= 2;
1630 xscale
->dbr0_used
= 0;
1631 xscale
->dbr1_used
= 0;
1633 /* mark all hardware breakpoints as unset */
1636 if (breakpoint
->type
== BKPT_HARD
)
1638 breakpoint
->set
= 0;
1640 breakpoint
= breakpoint
->next
;
1643 if (!xscale
->handler_installed
)
1646 jtag_add_reset(0, 0);
1648 /* wait 300ms; 150 and 100ms were not enough */
1649 jtag_add_sleep(300*1000);
1651 jtag_add_runtest(2030, TAP_RTI
);
1652 jtag_execute_queue();
1654 /* set Hold reset, Halt mode and Trap Reset */
1655 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1656 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1657 xscale_write_dcsr(target
, 1, 0);
1659 /* Load debug handler */
1660 if (fileio_open(&debug_handler
, PKGLIBDIR
"/xscale/debug_handler.bin", FILEIO_READ
, FILEIO_BINARY
) != ERROR_OK
)
1662 ERROR("file open error: %s", debug_handler
.error_str
);
1666 if ((binary_size
= debug_handler
.size
) % 4)
1668 ERROR("debug_handler.bin: size not a multiple of 4");
1672 if (binary_size
> 0x800)
1674 ERROR("debug_handler.bin: larger than 2kb");
1678 binary_size
= CEIL(binary_size
, 32) * 32;
1680 address
= xscale
->handler_address
;
1681 while (binary_size
> 0)
1686 if ((retval
= fileio_read(&debug_handler
, 32, buffer
, &buf_cnt
)) != ERROR_OK
)
1688 ERROR("reading debug handler failed: %s", debug_handler
.error_str
);
1691 for (i
= 0; i
< buf_cnt
; i
+= 4)
1693 /* convert LE buffer to host-endian u32 */
1694 cache_line
[i
/ 4] = le_to_h_u32(&buffer
[i
]);
1697 for (; buf_cnt
< 32; buf_cnt
+= 4)
1699 cache_line
[buf_cnt
/ 4] = 0xe1a08008;
1702 /* only load addresses other than the reset vectors */
1703 if ((address
% 0x400) != 0x0)
1705 xscale_load_ic(target
, 1, address
, cache_line
);
1709 binary_size
-= buf_cnt
;
1712 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
1713 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
1715 jtag_add_runtest(30, TAP_RTI
);
1717 jtag_add_sleep(100000);
1719 /* set Hold reset, Halt mode and Trap Reset */
1720 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1721 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1722 xscale_write_dcsr(target
, 1, 0);
1724 /* clear Hold reset to let the target run (should enter debug handler) */
1725 xscale_write_dcsr(target
, 0, 1);
1726 target
->state
= TARGET_RUNNING
;
1728 if ((target
->reset_mode
!= RESET_HALT
) && (target
->reset_mode
!= RESET_INIT
))
1730 jtag_add_sleep(10000);
1732 /* we should have entered debug now */
1733 xscale_debug_entry(target
);
1734 target
->state
= TARGET_HALTED
;
1736 /* resume the target */
1737 xscale_resume(target
, 1, 0x0, 1, 0);
1740 fileio_close(&debug_handler
);
1744 jtag_add_reset(0, 0);
1751 int xscale_soft_reset_halt(struct target_s
*target
)
1757 int xscale_prepare_reset_halt(struct target_s
*target
)
1759 /* nothing to be done for reset_halt on XScale targets
1760 * we always halt after a reset to upload the debug handler
1765 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
)
1771 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
)
1777 int xscale_full_context(target_t
*target
)
1779 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1787 if (target
->state
!= TARGET_HALTED
)
1789 WARNING("target not halted");
1790 return ERROR_TARGET_NOT_HALTED
;
1793 buffer
= malloc(4 * 8);
1795 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1796 * we can't enter User mode on an XScale (unpredictable),
1797 * but User shares registers with SYS
1799 for(i
= 1; i
< 7; i
++)
1803 /* check if there are invalid registers in the current mode
1805 for (j
= 0; j
<= 16; j
++)
1807 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
== 0)
1815 /* request banked registers */
1816 xscale_send_u32(target
, 0x0);
1819 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1820 tmp_cpsr
|= 0xc0; /* I/F bits */
1822 /* send CPSR for desired mode */
1823 xscale_send_u32(target
, tmp_cpsr
);
1825 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1826 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1828 xscale_receive(target
, buffer
, 8);
1829 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1830 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1831 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).valid
= 1;
1835 xscale_receive(target
, buffer
, 7);
1838 /* move data from buffer to register cache */
1839 for (j
= 8; j
<= 14; j
++)
1841 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]);
1842 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1843 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
= 1;
1853 int xscale_restore_context(target_t
*target
)
1855 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1861 if (target
->state
!= TARGET_HALTED
)
1863 WARNING("target not halted");
1864 return ERROR_TARGET_NOT_HALTED
;
1867 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1868 * we can't enter User mode on an XScale (unpredictable),
1869 * but User shares registers with SYS
1871 for(i
= 1; i
< 7; i
++)
1875 /* check if there are invalid registers in the current mode
1877 for (j
= 8; j
<= 14; j
++)
1879 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
== 1)
1883 /* if not USR/SYS, check if the SPSR needs to be written */
1884 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1886 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
== 1)
1894 /* send banked registers */
1895 xscale_send_u32(target
, 0x1);
1898 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1899 tmp_cpsr
|= 0xc0; /* I/F bits */
1901 /* send CPSR for desired mode */
1902 xscale_send_u32(target
, tmp_cpsr
);
1904 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1905 for (j
= 8; j
<= 14; j
++)
1907 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, j
).value
, 0, 32));
1908 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1911 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1913 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32));
1914 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1922 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1924 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1925 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1929 DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1931 if (target
->state
!= TARGET_HALTED
)
1933 WARNING("target not halted");
1934 return ERROR_TARGET_NOT_HALTED
;
1937 /* sanitize arguments */
1938 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1939 return ERROR_INVALID_ARGUMENTS
;
1941 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1942 return ERROR_TARGET_UNALIGNED_ACCESS
;
1944 /* send memory read request (command 0x1n, n: access size) */
1945 xscale_send_u32(target
, 0x10 | size
);
1947 /* send base address for read request */
1948 xscale_send_u32(target
, address
);
1950 /* send number of requested data words */
1951 xscale_send_u32(target
, count
);
1953 /* receive data from target (count times 32-bit words in host endianness) */
1954 buf32
= malloc(4 * count
);
1955 xscale_receive(target
, buf32
, count
);
1957 /* extract data from host-endian buffer into byte stream */
1958 for (i
= 0; i
< count
; i
++)
1963 target_buffer_set_u32(target
, buffer
, buf32
[i
]);
1967 target_buffer_set_u16(target
, buffer
, buf32
[i
] & 0xffff);
1971 *buffer
++ = buf32
[i
] & 0xff;
1974 ERROR("should never get here");
1981 /* examine DCSR, to see if Sticky Abort (SA) got set */
1982 xscale_read_dcsr(target
);
1983 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1986 xscale_send_u32(target
, 0x60);
1988 return ERROR_TARGET_DATA_ABORT
;
1994 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1996 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1997 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1999 DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
2001 if (target
->state
!= TARGET_HALTED
)
2003 WARNING("target not halted");
2004 return ERROR_TARGET_NOT_HALTED
;
2007 /* sanitize arguments */
2008 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
2009 return ERROR_INVALID_ARGUMENTS
;
2011 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
2012 return ERROR_TARGET_UNALIGNED_ACCESS
;
2014 /* send memory write request (command 0x2n, n: access size) */
2015 xscale_send_u32(target
, 0x20 | size
);
2017 /* send base address for read request */
2018 xscale_send_u32(target
, address
);
2020 /* send number of requested data words to be written*/
2021 xscale_send_u32(target
, count
);
2023 /* extract data from host-endian buffer into byte stream */
2025 for (i
= 0; i
< count
; i
++)
2030 value
= target_buffer_get_u32(target
, buffer
);
2031 xscale_send_u32(target
, value
);
2035 value
= target_buffer_get_u16(target
, buffer
);
2036 xscale_send_u32(target
, value
);
2041 xscale_send_u32(target
, value
);
2045 ERROR("should never get here");
2050 xscale_send(target
, buffer
, count
, size
);
2052 /* examine DCSR, to see if Sticky Abort (SA) got set */
2053 xscale_read_dcsr(target
);
2054 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
2057 xscale_send_u32(target
, 0x60);
2059 return ERROR_TARGET_DATA_ABORT
;
2065 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
)
2067 return xscale_write_memory(target
, address
, 4, count
, buffer
);
2070 int xscale_checksum_memory(struct target_s
*target
, u32 address
, u32 count
, u32
* checksum
)
2072 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2075 u32
xscale_get_ttb(target_t
*target
)
2077 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2078 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2081 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_TTB
]);
2082 ttb
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_TTB
].value
, 0, 32);
2087 void xscale_disable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2089 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2090 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2093 /* read cp15 control register */
2094 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2095 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2098 cp15_control
&= ~0x1U
;
2103 xscale_send_u32(target
, 0x50);
2104 xscale_send_u32(target
, xscale
->cache_clean_address
);
2106 /* invalidate DCache */
2107 xscale_send_u32(target
, 0x51);
2109 cp15_control
&= ~0x4U
;
2114 /* invalidate ICache */
2115 xscale_send_u32(target
, 0x52);
2116 cp15_control
&= ~0x1000U
;
2119 /* write new cp15 control register */
2120 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2122 /* execute cpwait to ensure outstanding operations complete */
2123 xscale_send_u32(target
, 0x53);
2126 void xscale_enable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2128 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2129 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2132 /* read cp15 control register */
2133 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2134 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2137 cp15_control
|= 0x1U
;
2140 cp15_control
|= 0x4U
;
2143 cp15_control
|= 0x1000U
;
2145 /* write new cp15 control register */
2146 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2148 /* execute cpwait to ensure outstanding operations complete */
2149 xscale_send_u32(target
, 0x53);
2152 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2154 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2155 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2157 if (target
->state
!= TARGET_HALTED
)
2159 WARNING("target not halted");
2160 return ERROR_TARGET_NOT_HALTED
;
2163 if (xscale
->force_hw_bkpts
)
2164 breakpoint
->type
= BKPT_HARD
;
2166 if (breakpoint
->set
)
2168 WARNING("breakpoint already set");
2172 if (breakpoint
->type
== BKPT_HARD
)
2174 u32 value
= breakpoint
->address
| 1;
2175 if (!xscale
->ibcr0_used
)
2177 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], value
);
2178 xscale
->ibcr0_used
= 1;
2179 breakpoint
->set
= 1; /* breakpoint set on first breakpoint register */
2181 else if (!xscale
->ibcr1_used
)
2183 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], value
);
2184 xscale
->ibcr1_used
= 1;
2185 breakpoint
->set
= 2; /* breakpoint set on second breakpoint register */
2189 ERROR("BUG: no hardware comparator available");
2193 else if (breakpoint
->type
== BKPT_SOFT
)
2195 if (breakpoint
->length
== 4)
2197 /* keep the original instruction in target endianness */
2198 target
->type
->read_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2199 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2200 target_write_u32(target
, breakpoint
->address
, xscale
->arm_bkpt
);
2204 /* keep the original instruction in target endianness */
2205 target
->type
->read_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2206 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2207 target_write_u32(target
, breakpoint
->address
, xscale
->thumb_bkpt
);
2209 breakpoint
->set
= 1;
2216 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2218 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2219 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2221 if (target
->state
!= TARGET_HALTED
)
2223 WARNING("target not halted");
2224 return ERROR_TARGET_NOT_HALTED
;
2227 if (xscale
->force_hw_bkpts
)
2229 DEBUG("forcing use of hardware breakpoint at address 0x%8.8x", breakpoint
->address
);
2230 breakpoint
->type
= BKPT_HARD
;
2233 if ((breakpoint
->type
== BKPT_HARD
) && (xscale
->ibcr_available
< 1))
2235 INFO("no breakpoint unit available for hardware breakpoint");
2236 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2240 xscale
->ibcr_available
--;
2243 if ((breakpoint
->length
!= 2) && (breakpoint
->length
!= 4))
2245 INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2246 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2252 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2254 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2255 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2257 if (target
->state
!= TARGET_HALTED
)
2259 WARNING("target not halted");
2260 return ERROR_TARGET_NOT_HALTED
;
2263 if (!breakpoint
->set
)
2265 WARNING("breakpoint not set");
2269 if (breakpoint
->type
== BKPT_HARD
)
2271 if (breakpoint
->set
== 1)
2273 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], 0x0);
2274 xscale
->ibcr0_used
= 0;
2276 else if (breakpoint
->set
== 2)
2278 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], 0x0);
2279 xscale
->ibcr1_used
= 0;
2281 breakpoint
->set
= 0;
2285 /* restore original instruction (kept in target endianness) */
2286 if (breakpoint
->length
== 4)
2288 target
->type
->write_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2292 target
->type
->write_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2294 breakpoint
->set
= 0;
2300 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2302 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2303 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2305 if (target
->state
!= TARGET_HALTED
)
2307 WARNING("target not halted");
2308 return ERROR_TARGET_NOT_HALTED
;
2311 if (breakpoint
->set
)
2313 xscale_unset_breakpoint(target
, breakpoint
);
2316 if (breakpoint
->type
== BKPT_HARD
)
2317 xscale
->ibcr_available
++;
2322 int xscale_set_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2324 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2325 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2327 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2328 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2330 if (target
->state
!= TARGET_HALTED
)
2332 WARNING("target not halted");
2333 return ERROR_TARGET_NOT_HALTED
;
2336 xscale_get_reg(dbcon
);
2338 switch (watchpoint
->rw
)
2350 ERROR("BUG: watchpoint->rw neither read, write nor access");
2353 if (!xscale
->dbr0_used
)
2355 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR0
], watchpoint
->address
);
2356 dbcon_value
|= enable
;
2357 xscale_set_reg_u32(dbcon
, dbcon_value
);
2358 watchpoint
->set
= 1;
2359 xscale
->dbr0_used
= 1;
2361 else if (!xscale
->dbr1_used
)
2363 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR1
], watchpoint
->address
);
2364 dbcon_value
|= enable
<< 2;
2365 xscale_set_reg_u32(dbcon
, dbcon_value
);
2366 watchpoint
->set
= 2;
2367 xscale
->dbr1_used
= 1;
2371 ERROR("BUG: no hardware comparator available");
2378 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2380 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2381 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2383 if (target
->state
!= TARGET_HALTED
)
2385 WARNING("target not halted");
2386 return ERROR_TARGET_NOT_HALTED
;
2389 if (xscale
->dbr_available
< 1)
2391 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2394 if ((watchpoint
->length
!= 1) && (watchpoint
->length
!= 2) && (watchpoint
->length
!= 4))
2396 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2399 xscale
->dbr_available
--;
2404 int xscale_unset_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2406 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2407 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2408 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2409 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2411 if (target
->state
!= TARGET_HALTED
)
2413 WARNING("target not halted");
2414 return ERROR_TARGET_NOT_HALTED
;
2417 if (!watchpoint
->set
)
2419 WARNING("breakpoint not set");
2423 if (watchpoint
->set
== 1)
2425 dbcon_value
&= ~0x3;
2426 xscale_set_reg_u32(dbcon
, dbcon_value
);
2427 xscale
->dbr0_used
= 0;
2429 else if (watchpoint
->set
== 2)
2431 dbcon_value
&= ~0xc;
2432 xscale_set_reg_u32(dbcon
, dbcon_value
);
2433 xscale
->dbr1_used
= 0;
2435 watchpoint
->set
= 0;
2440 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2442 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2443 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2445 if (target
->state
!= TARGET_HALTED
)
2447 WARNING("target not halted");
2448 return ERROR_TARGET_NOT_HALTED
;
2451 if (watchpoint
->set
)
2453 xscale_unset_watchpoint(target
, watchpoint
);
2456 xscale
->dbr_available
++;
2461 void xscale_enable_watchpoints(struct target_s
*target
)
2463 watchpoint_t
*watchpoint
= target
->watchpoints
;
2467 if (watchpoint
->set
== 0)
2468 xscale_set_watchpoint(target
, watchpoint
);
2469 watchpoint
= watchpoint
->next
;
2473 void xscale_enable_breakpoints(struct target_s
*target
)
2475 breakpoint_t
*breakpoint
= target
->breakpoints
;
2477 /* set any pending breakpoints */
2480 if (breakpoint
->set
== 0)
2481 xscale_set_breakpoint(target
, breakpoint
);
2482 breakpoint
= breakpoint
->next
;
2486 int xscale_get_reg(reg_t
*reg
)
2488 xscale_reg_t
*arch_info
= reg
->arch_info
;
2489 target_t
*target
= arch_info
->target
;
2490 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2491 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2493 /* DCSR, TX and RX are accessible via JTAG */
2494 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2496 return xscale_read_dcsr(arch_info
->target
);
2498 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2500 /* 1 = consume register content */
2501 return xscale_read_tx(arch_info
->target
, 1);
2503 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2505 /* can't read from RX register (host -> debug handler) */
2508 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2510 /* can't (explicitly) read from TXRXCTRL register */
2513 else /* Other DBG registers have to be transfered by the debug handler */
2515 /* send CP read request (command 0x40) */
2516 xscale_send_u32(target
, 0x40);
2518 /* send CP register number */
2519 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2521 /* read register value */
2522 xscale_read_tx(target
, 1);
2523 buf_cpy(xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
, reg
->value
, 32);
2532 int xscale_set_reg(reg_t
*reg
, u8
* buf
)
2534 xscale_reg_t
*arch_info
= reg
->arch_info
;
2535 target_t
*target
= arch_info
->target
;
2536 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2537 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2538 u32 value
= buf_get_u32(buf
, 0, 32);
2540 /* DCSR, TX and RX are accessible via JTAG */
2541 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2543 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32, value
);
2544 return xscale_write_dcsr(arch_info
->target
, -1, -1);
2546 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2548 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
2549 return xscale_write_rx(arch_info
->target
);
2551 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2553 /* can't write to TX register (debug-handler -> host) */
2556 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2558 /* can't (explicitly) write to TXRXCTRL register */
2561 else /* Other DBG registers have to be transfered by the debug handler */
2563 /* send CP write request (command 0x41) */
2564 xscale_send_u32(target
, 0x41);
2566 /* send CP register number */
2567 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2569 /* send CP register value */
2570 xscale_send_u32(target
, value
);
2571 buf_set_u32(reg
->value
, 0, 32, value
);
2577 /* convenience wrapper to access XScale specific registers */
2578 int xscale_set_reg_u32(reg_t
*reg
, u32 value
)
2582 buf_set_u32(buf
, 0, 32, value
);
2584 return xscale_set_reg(reg
, buf
);
2587 int xscale_write_dcsr_sw(target_t
*target
, u32 value
)
2589 /* get pointers to arch-specific information */
2590 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2591 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2592 reg_t
*dcsr
= &xscale
->reg_cache
->reg_list
[XSCALE_DCSR
];
2593 xscale_reg_t
*dcsr_arch_info
= dcsr
->arch_info
;
2595 /* send CP write request (command 0x41) */
2596 xscale_send_u32(target
, 0x41);
2598 /* send CP register number */
2599 xscale_send_u32(target
, dcsr_arch_info
->dbg_handler_number
);
2601 /* send CP register value */
2602 xscale_send_u32(target
, value
);
2603 buf_set_u32(dcsr
->value
, 0, 32, value
);
2608 int xscale_read_trace(target_t
*target
)
2610 /* get pointers to arch-specific information */
2611 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2612 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2613 xscale_trace_data_t
**trace_data_p
;
2615 /* 258 words from debug handler
2616 * 256 trace buffer entries
2617 * 2 checkpoint addresses
2619 u32 trace_buffer
[258];
2620 int is_address
[256];
2623 if (target
->state
!= TARGET_HALTED
)
2625 WARNING("target must be stopped to read trace data");
2626 return ERROR_TARGET_NOT_HALTED
;
2629 /* send read trace buffer command (command 0x61) */
2630 xscale_send_u32(target
, 0x61);
2632 /* receive trace buffer content */
2633 xscale_receive(target
, trace_buffer
, 258);
2635 /* parse buffer backwards to identify address entries */
2636 for (i
= 255; i
>= 0; i
--)
2639 if (((trace_buffer
[i
] & 0xf0) == 0x90) ||
2640 ((trace_buffer
[i
] & 0xf0) == 0xd0))
2643 is_address
[--i
] = 1;
2645 is_address
[--i
] = 1;
2647 is_address
[--i
] = 1;
2649 is_address
[--i
] = 1;
2654 /* search first non-zero entry */
2655 for (j
= 0; (j
< 256) && (trace_buffer
[j
] == 0) && (!is_address
[j
]); j
++)
2660 DEBUG("no trace data collected");
2661 return ERROR_XSCALE_NO_TRACE_DATA
;
2664 for (trace_data_p
= &xscale
->trace
.data
; *trace_data_p
; trace_data_p
= &(*trace_data_p
)->next
)
2667 *trace_data_p
= malloc(sizeof(xscale_trace_data_t
));
2668 (*trace_data_p
)->next
= NULL
;
2669 (*trace_data_p
)->chkpt0
= trace_buffer
[256];
2670 (*trace_data_p
)->chkpt1
= trace_buffer
[257];
2671 (*trace_data_p
)->last_instruction
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
2672 (*trace_data_p
)->entries
= malloc(sizeof(xscale_trace_entry_t
) * (256 - j
));
2673 (*trace_data_p
)->depth
= 256 - j
;
2675 for (i
= j
; i
< 256; i
++)
2677 (*trace_data_p
)->entries
[i
- j
].data
= trace_buffer
[i
];
2679 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_ADDRESS
;
2681 (*trace_data_p
)->entries
[i
- j
].type
= XSCALE_TRACE_MESSAGE
;
2687 int xscale_read_instruction(target_t
*target
, arm_instruction_t
*instruction
)
2689 /* get pointers to arch-specific information */
2690 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2691 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2698 if (!xscale
->trace
.image
)
2699 return ERROR_TRACE_IMAGE_UNAVAILABLE
;
2701 /* search for the section the current instruction belongs to */
2702 for (i
= 0; i
< xscale
->trace
.image
->num_sections
; i
++)
2704 if ((xscale
->trace
.image
->sections
[i
].base_address
<= xscale
->trace
.current_pc
) &&
2705 (xscale
->trace
.image
->sections
[i
].base_address
+ xscale
->trace
.image
->sections
[i
].size
> xscale
->trace
.current_pc
))
2714 /* current instruction couldn't be found in the image */
2715 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2718 if (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
)
2721 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2722 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2723 4, buf
, &size_read
)) != ERROR_OK
)
2725 ERROR("error while reading instruction: %i", retval
);
2726 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2728 opcode
= target_buffer_get_u32(target
, buf
);
2729 arm_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2731 else if (xscale
->trace
.core_state
== ARMV4_5_STATE_THUMB
)
2734 if ((retval
= image_read_section(xscale
->trace
.image
, section
,
2735 xscale
->trace
.current_pc
- xscale
->trace
.image
->sections
[section
].base_address
,
2736 2, buf
, &size_read
)) != ERROR_OK
)
2738 ERROR("error while reading instruction: %i", retval
);
2739 return ERROR_TRACE_INSTRUCTION_UNAVAILABLE
;
2741 opcode
= target_buffer_get_u16(target
, buf
);
2742 thumb_evaluate_opcode(opcode
, xscale
->trace
.current_pc
, instruction
);
2746 ERROR("BUG: unknown core state encountered");
2753 int xscale_branch_address(xscale_trace_data_t
*trace_data
, int i
, u32
*target
)
2755 /* if there are less than four entries prior to the indirect branch message
2756 * we can't extract the address */
2762 *target
= (trace_data
->entries
[i
-1].data
) | (trace_data
->entries
[i
-2].data
<< 8) |
2763 (trace_data
->entries
[i
-3].data
<< 16) | (trace_data
->entries
[i
-4].data
<< 24);
2768 int xscale_analyze_trace(target_t
*target
, command_context_t
*cmd_ctx
)
2770 /* get pointers to arch-specific information */
2771 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2772 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2775 xscale_trace_data_t
*trace_data
= xscale
->trace
.data
;
2784 xscale
->trace
.core_state
= ARMV4_5_STATE_ARM
;
2789 for (i
= 0; i
< trace_data
->depth
; i
++)
2795 if (trace_data
->entries
[i
].type
== XSCALE_TRACE_ADDRESS
)
2798 switch ((trace_data
->entries
[i
].data
& 0xf0) >> 4)
2800 case 0: /* Exceptions */
2808 exception
= (trace_data
->entries
[i
].data
& 0x70) >> 4;
2810 next_pc
= (trace_data
->entries
[i
].data
& 0xf0) >> 2;
2811 command_print(cmd_ctx
, "--- exception %i ---", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2813 case 8: /* Direct Branch */
2816 case 9: /* Indirect Branch */
2818 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2823 case 13: /* Checkpointed Indirect Branch */
2824 if (xscale_branch_address(trace_data
, i
, &next_pc
) == 0)
2827 if (((chkpt
== 0) && (next_pc
!= trace_data
->chkpt0
))
2828 || ((chkpt
== 1) && (next_pc
!= trace_data
->chkpt1
)))
2829 WARNING("checkpointed indirect branch target address doesn't match checkpoint");
2831 /* explicit fall-through */
2832 case 12: /* Checkpointed Direct Branch */
2837 next_pc
= trace_data
->chkpt0
;
2840 else if (chkpt
== 1)
2843 next_pc
= trace_data
->chkpt0
;
2848 WARNING("more than two checkpointed branches encountered");
2851 case 15: /* Roll-over */
2854 default: /* Reserved */
2855 command_print(cmd_ctx
, "--- reserved trace message ---");
2856 ERROR("BUG: trace message %i is reserved", (trace_data
->entries
[i
].data
& 0xf0) >> 4);
2860 if (xscale
->trace
.pc_ok
)
2862 int executed
= (trace_data
->entries
[i
].data
& 0xf) + rollover
* 16;
2863 arm_instruction_t instruction
;
2865 if ((exception
== 6) || (exception
== 7))
2867 /* IRQ or FIQ exception, no instruction executed */
2871 while (executed
-- >= 0)
2873 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2875 /* can't continue tracing with no image available */
2876 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2880 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2882 /* TODO: handle incomplete images */
2886 /* a precise abort on a load to the PC is included in the incremental
2887 * word count, other instructions causing data aborts are not included
2889 if ((executed
== 0) && (exception
== 4)
2890 && ((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDM
)))
2892 if ((instruction
.type
== ARM_LDM
)
2893 && ((instruction
.info
.load_store_multiple
.register_list
& 0x8000) == 0))
2897 else if (((instruction
.type
>= ARM_LDR
) && (instruction
.type
<= ARM_LDRSH
))
2898 && (instruction
.info
.load_store
.Rd
!= 15))
2904 /* only the last instruction executed
2905 * (the one that caused the control flow change)
2906 * could be a taken branch
2908 if (((executed
== -1) && (branch
== 1)) &&
2909 (((instruction
.type
== ARM_B
) ||
2910 (instruction
.type
== ARM_BL
) ||
2911 (instruction
.type
== ARM_BLX
)) &&
2912 (instruction
.info
.b_bl_bx_blx
.target_address
!= -1)))
2914 xscale
->trace
.current_pc
= instruction
.info
.b_bl_bx_blx
.target_address
;
2918 xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2;
2920 command_print(cmd_ctx
, "%s", instruction
.text
);
2928 xscale
->trace
.current_pc
= next_pc
;
2929 xscale
->trace
.pc_ok
= 1;
2933 for (; xscale
->trace
.current_pc
< trace_data
->last_instruction
; xscale
->trace
.current_pc
+= (xscale
->trace
.core_state
== ARMV4_5_STATE_ARM
) ? 4 : 2)
2935 arm_instruction_t instruction
;
2936 if ((retval
= xscale_read_instruction(target
, &instruction
)) != ERROR_OK
)
2938 /* can't continue tracing with no image available */
2939 if (retval
== ERROR_TRACE_IMAGE_UNAVAILABLE
)
2943 else if (retval
== ERROR_TRACE_INSTRUCTION_UNAVAILABLE
)
2945 /* TODO: handle incomplete images */
2948 command_print(cmd_ctx
, "%s", instruction
.text
);
2951 trace_data
= trace_data
->next
;
2957 void xscale_build_reg_cache(target_t
*target
)
2959 /* get pointers to arch-specific information */
2960 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2961 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2963 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
2964 xscale_reg_t
*arch_info
= malloc(sizeof(xscale_reg_arch_info
));
2966 int num_regs
= sizeof(xscale_reg_arch_info
) / sizeof(xscale_reg_t
);
2968 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
2969 armv4_5
->core_cache
= (*cache_p
);
2971 /* register a register arch-type for XScale dbg registers only once */
2972 if (xscale_reg_arch_type
== -1)
2973 xscale_reg_arch_type
= register_reg_arch_type(xscale_get_reg
, xscale_set_reg
);
2975 (*cache_p
)->next
= malloc(sizeof(reg_cache_t
));
2976 cache_p
= &(*cache_p
)->next
;
2978 /* fill in values for the xscale reg cache */
2979 (*cache_p
)->name
= "XScale registers";
2980 (*cache_p
)->next
= NULL
;
2981 (*cache_p
)->reg_list
= malloc(num_regs
* sizeof(reg_t
));
2982 (*cache_p
)->num_regs
= num_regs
;
2984 for (i
= 0; i
< num_regs
; i
++)
2986 (*cache_p
)->reg_list
[i
].name
= xscale_reg_list
[i
];
2987 (*cache_p
)->reg_list
[i
].value
= calloc(4, 1);
2988 (*cache_p
)->reg_list
[i
].dirty
= 0;
2989 (*cache_p
)->reg_list
[i
].valid
= 0;
2990 (*cache_p
)->reg_list
[i
].size
= 32;
2991 (*cache_p
)->reg_list
[i
].bitfield_desc
= NULL
;
2992 (*cache_p
)->reg_list
[i
].num_bitfields
= 0;
2993 (*cache_p
)->reg_list
[i
].arch_info
= &arch_info
[i
];
2994 (*cache_p
)->reg_list
[i
].arch_type
= xscale_reg_arch_type
;
2995 arch_info
[i
] = xscale_reg_arch_info
[i
];
2996 arch_info
[i
].target
= target
;
2999 xscale
->reg_cache
= (*cache_p
);
3002 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
3004 if (startup_mode
!= DAEMON_RESET
)
3006 ERROR("XScale target requires a reset");
3007 ERROR("Reset target to enable debug");
3010 /* assert TRST once during startup */
3011 jtag_add_reset(1, 0);
3012 jtag_add_sleep(5000);
3013 jtag_add_reset(0, 0);
3014 jtag_execute_queue();
3025 int xscale_init_arch_info(target_t
*target
, xscale_common_t
*xscale
, int chain_pos
, char *variant
)
3027 armv4_5_common_t
*armv4_5
;
3028 u32 high_reset_branch
, low_reset_branch
;
3031 armv4_5
= &xscale
->armv4_5_common
;
3033 /* store architecture specfic data (none so far) */
3034 xscale
->arch_info
= NULL
;
3035 xscale
->common_magic
= XSCALE_COMMON_MAGIC
;
3037 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
3038 xscale
->variant
= strdup(variant
);
3040 /* prepare JTAG information for the new target */
3041 xscale
->jtag_info
.chain_pos
= chain_pos
;
3042 jtag_register_event_callback(xscale_jtag_callback
, target
);
3044 xscale
->jtag_info
.dbgrx
= 0x02;
3045 xscale
->jtag_info
.dbgtx
= 0x10;
3046 xscale
->jtag_info
.dcsr
= 0x09;
3047 xscale
->jtag_info
.ldic
= 0x07;
3049 if ((strcmp(xscale
->variant
, "pxa250") == 0) ||
3050 (strcmp(xscale
->variant
, "pxa255") == 0) ||
3051 (strcmp(xscale
->variant
, "pxa26x") == 0))
3053 xscale
->jtag_info
.ir_length
= 5;
3055 else if ((strcmp(xscale
->variant
, "pxa27x") == 0) ||
3056 (strcmp(xscale
->variant
, "ixp42x") == 0) ||
3057 (strcmp(xscale
->variant
, "ixp45x") == 0) ||
3058 (strcmp(xscale
->variant
, "ixp46x") == 0))
3060 xscale
->jtag_info
.ir_length
= 7;
3063 /* the debug handler isn't installed (and thus not running) at this time */
3064 xscale
->handler_installed
= 0;
3065 xscale
->handler_running
= 0;
3066 xscale
->handler_address
= 0xfe000800;
3068 /* clear the vectors we keep locally for reference */
3069 memset(xscale
->low_vectors
, 0, sizeof(xscale
->low_vectors
));
3070 memset(xscale
->high_vectors
, 0, sizeof(xscale
->high_vectors
));
3072 /* no user-specified vectors have been configured yet */
3073 xscale
->static_low_vectors_set
= 0x0;
3074 xscale
->static_high_vectors_set
= 0x0;
3076 /* calculate branches to debug handler */
3077 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
3078 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
3080 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
3081 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
3083 for (i
= 1; i
<= 7; i
++)
3085 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3086 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
3089 /* 64kB aligned region used for DCache cleaning */
3090 xscale
->cache_clean_address
= 0xfffe0000;
3092 xscale
->hold_rst
= 0;
3093 xscale
->external_debug_break
= 0;
3095 xscale
->force_hw_bkpts
= 1;
3097 xscale
->ibcr_available
= 2;
3098 xscale
->ibcr0_used
= 0;
3099 xscale
->ibcr1_used
= 0;
3101 xscale
->dbr_available
= 2;
3102 xscale
->dbr0_used
= 0;
3103 xscale
->dbr1_used
= 0;
3105 xscale
->arm_bkpt
= ARMV5_BKPT(0x0);
3106 xscale
->thumb_bkpt
= ARMV5_T_BKPT(0x0) & 0xffff;
3108 xscale
->vector_catch
= 0x1;
3110 xscale
->trace
.capture_status
= TRACE_IDLE
;
3111 xscale
->trace
.data
= NULL
;
3112 xscale
->trace
.image
= NULL
;
3113 xscale
->trace
.buffer_enabled
= 0;
3114 xscale
->trace
.buffer_fill
= 0;
3116 /* prepare ARMv4/5 specific information */
3117 armv4_5
->arch_info
= xscale
;
3118 armv4_5
->read_core_reg
= xscale_read_core_reg
;
3119 armv4_5
->write_core_reg
= xscale_write_core_reg
;
3120 armv4_5
->full_context
= xscale_full_context
;
3122 armv4_5_init_arch_info(target
, armv4_5
);
3124 xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
= -1;
3125 xscale
->armv4_5_mmu
.get_ttb
= xscale_get_ttb
;
3126 xscale
->armv4_5_mmu
.read_memory
= xscale_read_memory
;
3127 xscale
->armv4_5_mmu
.write_memory
= xscale_write_memory
;
3128 xscale
->armv4_5_mmu
.disable_mmu_caches
= xscale_disable_mmu_caches
;
3129 xscale
->armv4_5_mmu
.enable_mmu_caches
= xscale_enable_mmu_caches
;
3130 xscale
->armv4_5_mmu
.has_tiny_pages
= 1;
3131 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3133 xscale
->fast_memory_access
= 0;
3138 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
3139 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
)
3142 char *variant
= NULL
;
3143 xscale_common_t
*xscale
= malloc(sizeof(xscale_common_t
));
3147 ERROR("'target xscale' requires four arguments: <endianess> <startup_mode> <chain_pos> <variant>");
3151 chain_pos
= strtoul(args
[3], NULL
, 0);
3155 xscale_init_arch_info(target
, xscale
, chain_pos
, variant
);
3156 xscale_build_reg_cache(target
);
3161 int xscale_handle_debug_handler_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3163 target_t
*target
= NULL
;
3164 armv4_5_common_t
*armv4_5
;
3165 xscale_common_t
*xscale
;
3167 u32 handler_address
;
3171 ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
3175 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3177 ERROR("no target '%s' configured", args
[0]);
3181 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3186 handler_address
= strtoul(args
[1], NULL
, 0);
3188 if (((handler_address
>= 0x800) && (handler_address
<= 0x1fef800)) ||
3189 ((handler_address
>= 0xfe000800) && (handler_address
<= 0xfffff800)))
3191 xscale
->handler_address
= handler_address
;
3195 ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
3201 int xscale_handle_cache_clean_address_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3203 target_t
*target
= NULL
;
3204 armv4_5_common_t
*armv4_5
;
3205 xscale_common_t
*xscale
;
3207 u32 cache_clean_address
;
3211 ERROR("'xscale cache_clean_address <target#> <address>' command takes two required operands");
3215 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
3217 ERROR("no target '%s' configured", args
[0]);
3221 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3226 cache_clean_address
= strtoul(args
[1], NULL
, 0);
3228 if (cache_clean_address
& 0xffff)
3230 ERROR("xscale cache_clean_address <address> must be 64kb aligned");
3234 xscale
->cache_clean_address
= cache_clean_address
;
3240 int xscale_handle_cache_info_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3242 target_t
*target
= get_current_target(cmd_ctx
);
3243 armv4_5_common_t
*armv4_5
;
3244 xscale_common_t
*xscale
;
3246 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3251 return armv4_5_handle_cache_info_command(cmd_ctx
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
3254 static int xscale_virt2phys(struct target_s
*target
, u32
virtual, u32
*physical
)
3256 armv4_5_common_t
*armv4_5
;
3257 xscale_common_t
*xscale
;
3264 if ((retval
= xscale_get_arch_pointers(target
, &armv4_5
, &xscale
)) != ERROR_OK
)
3268 u32 ret
= armv4_5_mmu_translate_va(target
, &xscale
->armv4_5_mmu
, virtual, &type
, &cb
, &domain
, &ap
);
3278 static int xscale_mmu(struct target_s
*target
, int *enabled
)
3280 armv4_5_common_t
*armv4_5
= target
->arch_info
;
3281 xscale_common_t
*xscale
= armv4_5
->arch_info
;
3283 if (target
->state
!= TARGET_HALTED
)
3285 ERROR("Target not halted");
3286 return ERROR_TARGET_INVALID
;
3289 *enabled
= xscale
->armv4_5_mmu
.mmu_enabled
;
3293 int xscale_handle_mmu_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3295 target_t
*target
= get_current_target(cmd_ctx
);
3296 armv4_5_common_t
*armv4_5
;
3297 xscale_common_t
*xscale
;
3299 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3304 if (target
->state
!= TARGET_HALTED
)
3306 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3312 if (strcmp("enable", args
[0]) == 0)
3314 xscale_enable_mmu_caches(target
, 1, 0, 0);
3315 xscale
->armv4_5_mmu
.mmu_enabled
= 1;
3317 else if (strcmp("disable", args
[0]) == 0)
3319 xscale_disable_mmu_caches(target
, 1, 0, 0);
3320 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
3324 command_print(cmd_ctx
, "mmu %s", (xscale
->armv4_5_mmu
.mmu_enabled
) ? "enabled" : "disabled");
3329 int xscale_handle_idcache_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3331 target_t
*target
= get_current_target(cmd_ctx
);
3332 armv4_5_common_t
*armv4_5
;
3333 xscale_common_t
*xscale
;
3334 int icache
= 0, dcache
= 0;
3336 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3341 if (target
->state
!= TARGET_HALTED
)
3343 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3347 if (strcmp(cmd
, "icache") == 0)
3349 else if (strcmp(cmd
, "dcache") == 0)
3354 if (strcmp("enable", args
[0]) == 0)
3356 xscale_enable_mmu_caches(target
, 0, dcache
, icache
);
3359 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 1;
3361 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 1;
3363 else if (strcmp("disable", args
[0]) == 0)
3365 xscale_disable_mmu_caches(target
, 0, dcache
, icache
);
3368 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 0;
3370 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 0;
3375 command_print(cmd_ctx
, "icache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
) ? "enabled" : "disabled");
3378 command_print(cmd_ctx
, "dcache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
) ? "enabled" : "disabled");
3383 int xscale_handle_vector_catch_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3385 target_t
*target
= get_current_target(cmd_ctx
);
3386 armv4_5_common_t
*armv4_5
;
3387 xscale_common_t
*xscale
;
3389 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3396 command_print(cmd_ctx
, "usage: xscale vector_catch [mask]");
3400 xscale
->vector_catch
= strtoul(args
[0], NULL
, 0);
3401 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 8, xscale
->vector_catch
);
3402 xscale_write_dcsr(target
, -1, -1);
3405 command_print(cmd_ctx
, "vector catch mask: 0x%2.2x", xscale
->vector_catch
);
3410 int xscale_handle_force_hw_bkpts_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3412 target_t
*target
= get_current_target(cmd_ctx
);
3413 armv4_5_common_t
*armv4_5
;
3414 xscale_common_t
*xscale
;
3416 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3421 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3423 xscale
->force_hw_bkpts
= 1;
3425 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3427 xscale
->force_hw_bkpts
= 0;
3431 command_print(cmd_ctx
, "usage: xscale force_hw_bkpts <enable|disable>");
3434 command_print(cmd_ctx
, "force hardware breakpoints %s", (xscale
->force_hw_bkpts
) ? "enabled" : "disabled");
3439 int xscale_handle_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3441 target_t
*target
= get_current_target(cmd_ctx
);
3442 armv4_5_common_t
*armv4_5
;
3443 xscale_common_t
*xscale
;
3446 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3451 if (target
->state
!= TARGET_HALTED
)
3453 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3457 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3459 xscale_trace_data_t
*td
, *next_td
;
3460 xscale
->trace
.buffer_enabled
= 1;
3462 /* free old trace data */
3463 td
= xscale
->trace
.data
;
3473 xscale
->trace
.data
= NULL
;
3475 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3477 xscale
->trace
.buffer_enabled
= 0;
3480 if ((argc
>= 2) && (strcmp("fill", args
[1]) == 0))
3483 xscale
->trace
.buffer_fill
= strtoul(args
[2], NULL
, 0);
3485 xscale
->trace
.buffer_fill
= 1;
3487 else if ((argc
>= 2) && (strcmp("wrap", args
[1]) == 0))
3489 xscale
->trace
.buffer_fill
= -1;
3492 if (xscale
->trace
.buffer_enabled
)
3494 /* if we enable the trace buffer in fill-once
3495 * mode we know the address of the first instruction */
3496 xscale
->trace
.pc_ok
= 1;
3497 xscale
->trace
.current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
3501 /* otherwise the address is unknown, and we have no known good PC */
3502 xscale
->trace
.pc_ok
= 0;
3505 command_print(cmd_ctx
, "trace buffer %s (%s)",
3506 (xscale
->trace
.buffer_enabled
) ? "enabled" : "disabled",
3507 (xscale
->trace
.buffer_fill
> 0) ? "fill" : "wrap");
3509 dcsr_value
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32);
3510 if (xscale
->trace
.buffer_fill
>= 0)
3511 xscale_write_dcsr_sw(target
, (dcsr_value
& 0xfffffffc) | 2);
3513 xscale_write_dcsr_sw(target
, dcsr_value
& 0xfffffffc);
3518 int xscale_handle_trace_image_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3521 armv4_5_common_t
*armv4_5
;
3522 xscale_common_t
*xscale
;
3526 command_print(cmd_ctx
, "usage: xscale trace_image <file> [base address] [type]");
3530 target
= get_current_target(cmd_ctx
);
3532 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3537 if (xscale
->trace
.image
)
3539 image_close(xscale
->trace
.image
);
3540 free(xscale
->trace
.image
);
3541 command_print(cmd_ctx
, "previously loaded image found and closed");
3544 xscale
->trace
.image
= malloc(sizeof(image_t
));
3545 xscale
->trace
.image
->base_address_set
= 0;
3546 xscale
->trace
.image
->start_address_set
= 0;
3548 /* a base address isn't always necessary, default to 0x0 (i.e. don't relocate) */
3551 xscale
->trace
.image
->base_address_set
= 1;
3552 xscale
->trace
.image
->base_address
= strtoul(args
[1], NULL
, 0);
3556 xscale
->trace
.image
->base_address_set
= 0;
3559 if (image_open(xscale
->trace
.image
, args
[0], (argc
>= 3) ? args
[2] : NULL
) != ERROR_OK
)
3561 command_print(cmd_ctx
, "image opening error: %s", xscale
->trace
.image
->error_str
);
3562 free(xscale
->trace
.image
);
3563 xscale
->trace
.image
= NULL
;
3570 int xscale_handle_dump_trace_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3572 target_t
*target
= get_current_target(cmd_ctx
);
3573 armv4_5_common_t
*armv4_5
;
3574 xscale_common_t
*xscale
;
3575 xscale_trace_data_t
*trace_data
;
3578 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3583 if (target
->state
!= TARGET_HALTED
)
3585 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3591 command_print(cmd_ctx
, "usage: xscale dump_trace <file>");
3595 trace_data
= xscale
->trace
.data
;
3599 command_print(cmd_ctx
, "no trace data collected");
3603 if (fileio_open(&file
, args
[0], FILEIO_WRITE
, FILEIO_BINARY
) != ERROR_OK
)
3605 command_print(cmd_ctx
, "file open error: %s", file
.error_str
);
3613 fileio_write_u32(&file
, trace_data
->chkpt0
);
3614 fileio_write_u32(&file
, trace_data
->chkpt1
);
3615 fileio_write_u32(&file
, trace_data
->last_instruction
);
3616 fileio_write_u32(&file
, trace_data
->depth
);
3618 for (i
= 0; i
< trace_data
->depth
; i
++)
3619 fileio_write_u32(&file
, trace_data
->entries
[i
].data
| ((trace_data
->entries
[i
].type
& 0xffff) << 16));
3621 trace_data
= trace_data
->next
;
3624 fileio_close(&file
);
3629 int xscale_handle_analyze_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3631 target_t
*target
= get_current_target(cmd_ctx
);
3632 armv4_5_common_t
*armv4_5
;
3633 xscale_common_t
*xscale
;
3635 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3640 xscale_analyze_trace(target
, cmd_ctx
);
3645 int xscale_handle_cp15(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3647 target_t
*target
= get_current_target(cmd_ctx
);
3648 armv4_5_common_t
*armv4_5
;
3649 xscale_common_t
*xscale
;
3651 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3656 if (target
->state
!= TARGET_HALTED
)
3658 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3665 reg_no
= strtoul(args
[0], NULL
, 0);
3666 /*translate from xscale cp15 register no to openocd register*/
3670 reg_no
= XSCALE_MAINID
;
3673 reg_no
= XSCALE_CTRL
;
3676 reg_no
= XSCALE_TTB
;
3679 reg_no
= XSCALE_DAC
;
3682 reg_no
= XSCALE_FSR
;
3685 reg_no
= XSCALE_FAR
;
3688 reg_no
= XSCALE_PID
;
3691 reg_no
= XSCALE_CPACCESS
;
3694 command_print(cmd_ctx
, "invalid register number");
3695 return ERROR_INVALID_ARGUMENTS
;
3697 reg
= &xscale
->reg_cache
->reg_list
[reg_no
];
3704 /* read cp15 control register */
3705 xscale_get_reg(reg
);
3706 value
= buf_get_u32(reg
->value
, 0, 32);
3707 command_print(cmd_ctx
, "%s (/%i): 0x%x", reg
->name
, reg
->size
, value
);
3712 u32 value
= strtoul(args
[1], NULL
, 0);
3714 /* send CP write request (command 0x41) */
3715 xscale_send_u32(target
, 0x41);
3717 /* send CP register number */
3718 xscale_send_u32(target
, reg_no
);
3720 /* send CP register value */
3721 xscale_send_u32(target
, value
);
3723 /* execute cpwait to ensure outstanding operations complete */
3724 xscale_send_u32(target
, 0x53);
3728 command_print(cmd_ctx
, "usage: cp15 [register]<, [value]>");
3734 int handle_xscale_fast_memory_access_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3736 target_t
*target
= get_current_target(cmd_ctx
);
3737 armv4_5_common_t
*armv4_5
;
3738 xscale_common_t
*xscale
;
3740 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3747 if (strcmp("enable", args
[0]) == 0)
3749 xscale
->fast_memory_access
= 1;
3751 else if (strcmp("disable", args
[0]) == 0)
3753 xscale
->fast_memory_access
= 0;
3757 return ERROR_COMMAND_SYNTAX_ERROR
;
3761 return ERROR_COMMAND_SYNTAX_ERROR
;
3764 command_print(cmd_ctx
, "fast memory access is %s", (xscale
->fast_memory_access
) ? "enabled" : "disabled");
3769 int xscale_register_commands(struct command_context_s
*cmd_ctx
)
3771 command_t
*xscale_cmd
;
3773 xscale_cmd
= register_command(cmd_ctx
, NULL
, "xscale", NULL
, COMMAND_ANY
, "xscale specific commands");
3775 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");
3776 register_command(cmd_ctx
, xscale_cmd
, "cache_clean_address", xscale_handle_cache_clean_address_command
, COMMAND_ANY
, NULL
);
3778 register_command(cmd_ctx
, xscale_cmd
, "cache_info", xscale_handle_cache_info_command
, COMMAND_EXEC
, NULL
);
3779 register_command(cmd_ctx
, xscale_cmd
, "mmu", xscale_handle_mmu_command
, COMMAND_EXEC
, "['enable'|'disable'] the MMU");
3780 register_command(cmd_ctx
, xscale_cmd
, "icache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the ICache");
3781 register_command(cmd_ctx
, xscale_cmd
, "dcache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the DCache");
3783 register_command(cmd_ctx
, xscale_cmd
, "vector_catch", xscale_handle_idcache_command
, COMMAND_EXEC
, "<mask> of vectors that should be catched");
3785 register_command(cmd_ctx
, xscale_cmd
, "trace_buffer", xscale_handle_trace_buffer_command
, COMMAND_EXEC
, "<enable|disable> ['fill' [n]|'wrap']");
3787 register_command(cmd_ctx
, xscale_cmd
, "dump_trace", xscale_handle_dump_trace_command
, COMMAND_EXEC
, "dump content of trace buffer to <file>");
3788 register_command(cmd_ctx
, xscale_cmd
, "analyze_trace", xscale_handle_analyze_trace_buffer_command
, COMMAND_EXEC
, "analyze content of trace buffer");
3789 register_command(cmd_ctx
, xscale_cmd
, "trace_image", xscale_handle_trace_image_command
,
3790 COMMAND_EXEC
, "load image from <file> [base address]");
3792 register_command(cmd_ctx
, xscale_cmd
, "cp15", xscale_handle_cp15
, COMMAND_EXEC
, "access coproc 15 <register> [value]");
3793 register_command(cmd_ctx
, xscale_cmd
, "fast_memory_access", handle_xscale_fast_memory_access_command
,
3794 COMMAND_ANY
, "use fast memory accesses instead of slower but potentially unsafe slow accesses <enable|disable>");
3796 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)