1 /***************************************************************************
2 * Copyright (C) 2006 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 ***************************************************************************/
27 #include "arm_simulator.h"
30 #include "binarybuffer.h"
31 #include "time_support.h"
32 #include "breakpoints.h"
37 #include <sys/types.h>
43 int xscale_register_commands(struct command_context_s
*cmd_ctx
);
45 /* forward declarations */
46 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
);
47 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
50 int xscale_arch_state(struct target_s
*target
, char *buf
, int buf_size
);
51 enum target_state
xscale_poll(target_t
*target
);
52 int xscale_halt(target_t
*target
);
53 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
);
54 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
);
55 int xscale_debug_entry(target_t
*target
);
56 int xscale_restore_context(target_t
*target
);
58 int xscale_assert_reset(target_t
*target
);
59 int xscale_deassert_reset(target_t
*target
);
60 int xscale_soft_reset_halt(struct target_s
*target
);
62 int xscale_set_reg_u32(reg_t
*reg
, u32 value
);
64 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
);
65 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
);
67 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
68 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
69 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
);
71 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
72 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
73 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
74 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
);
75 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
76 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
);
77 void xscale_enable_watchpoints(struct target_s
*target
);
78 void xscale_enable_breakpoints(struct target_s
*target
);
80 target_type_t xscale_target
=
85 .arch_state
= xscale_arch_state
,
88 .resume
= xscale_resume
,
91 .assert_reset
= xscale_assert_reset
,
92 .deassert_reset
= xscale_deassert_reset
,
93 .soft_reset_halt
= xscale_soft_reset_halt
,
95 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
97 .read_memory
= xscale_read_memory
,
98 .write_memory
= xscale_write_memory
,
99 .bulk_write_memory
= xscale_bulk_write_memory
,
101 .run_algorithm
= armv4_5_run_algorithm
,
103 .add_breakpoint
= xscale_add_breakpoint
,
104 .remove_breakpoint
= xscale_remove_breakpoint
,
105 .add_watchpoint
= xscale_add_watchpoint
,
106 .remove_watchpoint
= xscale_remove_watchpoint
,
108 .register_commands
= xscale_register_commands
,
109 .target_command
= xscale_target_command
,
110 .init_target
= xscale_init_target
,
114 char* xscale_reg_list
[] =
116 "XSCALE_MAINID", /* 0 */
126 "XSCALE_IBCR0", /* 10 */
136 "XSCALE_RX", /* 20 */
140 xscale_reg_t xscale_reg_arch_info
[] =
142 {XSCALE_MAINID
, NULL
},
143 {XSCALE_CACHETYPE
, NULL
},
145 {XSCALE_AUXCTRL
, NULL
},
151 {XSCALE_CPACCESS
, NULL
},
152 {XSCALE_IBCR0
, NULL
},
153 {XSCALE_IBCR1
, NULL
},
156 {XSCALE_DBCON
, NULL
},
157 {XSCALE_TBREG
, NULL
},
158 {XSCALE_CHKPT0
, NULL
},
159 {XSCALE_CHKPT1
, NULL
},
160 {XSCALE_DCSR
, NULL
}, /* DCSR accessed via JTAG or SW */
161 {-1, NULL
}, /* TX accessed via JTAG */
162 {-1, NULL
}, /* RX accessed via JTAG */
163 {-1, NULL
}, /* TXRXCTRL implicit access via JTAG */
166 int xscale_reg_arch_type
= -1;
168 int xscale_get_reg(reg_t
*reg
);
169 int xscale_set_reg(reg_t
*reg
, u8
*buf
);
171 int xscale_get_arch_pointers(target_t
*target
, armv4_5_common_t
**armv4_5_p
, xscale_common_t
**xscale_p
)
173 armv4_5_common_t
*armv4_5
= target
->arch_info
;
174 xscale_common_t
*xscale
= armv4_5
->arch_info
;
176 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
181 if (xscale
->common_magic
!= XSCALE_COMMON_MAGIC
)
186 *armv4_5_p
= armv4_5
;
192 int xscale_jtag_set_instr(int chain_pos
, u32 new_instr
)
194 jtag_device_t
*device
= jtag_get_device(chain_pos
);
196 if (buf_get_u32(device
->cur_instr
, 0, device
->ir_length
) != new_instr
)
200 field
.device
= chain_pos
;
201 field
.num_bits
= device
->ir_length
;
202 field
.out_value
= calloc(CEIL(field
.num_bits
, 8), 1);
203 buf_set_u32(field
.out_value
, 0, field
.num_bits
, new_instr
);
204 field
.out_mask
= NULL
;
205 field
.in_value
= NULL
;
206 field
.in_check_value
= device
->expected
;
207 field
.in_check_mask
= device
->expected_mask
;
208 field
.in_handler
= NULL
;
209 field
.in_handler_priv
= NULL
;
211 jtag_add_ir_scan(1, &field
, -1);
213 free(field
.out_value
);
219 int xscale_jtag_callback(enum jtag_event event
, void *priv
)
223 case JTAG_TRST_ASSERTED
:
225 case JTAG_TRST_RELEASED
:
227 case JTAG_SRST_ASSERTED
:
229 case JTAG_SRST_RELEASED
:
232 WARNING("unhandled JTAG event");
238 int xscale_read_dcsr(target_t
*target
)
240 armv4_5_common_t
*armv4_5
= target
->arch_info
;
241 xscale_common_t
*xscale
= armv4_5
->arch_info
;
245 scan_field_t fields
[3];
247 u8 field0_check_value
= 0x2;
248 u8 field0_check_mask
= 0x7;
250 u8 field2_check_value
= 0x0;
251 u8 field2_check_mask
= 0x1;
253 jtag_add_end_state(TAP_PD
);
254 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
256 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
257 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
259 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
260 fields
[0].num_bits
= 3;
261 fields
[0].out_value
= &field0
;
262 fields
[0].out_mask
= NULL
;
263 fields
[0].in_value
= NULL
;
264 fields
[0].in_check_value
= &field0_check_value
;
265 fields
[0].in_check_mask
= &field0_check_mask
;
266 fields
[0].in_handler
= NULL
;
267 fields
[0].in_handler_priv
= NULL
;
269 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
270 fields
[1].num_bits
= 32;
271 fields
[1].out_value
= NULL
;
272 fields
[1].out_mask
= NULL
;
273 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
274 fields
[1].in_handler
= NULL
;
275 fields
[1].in_handler_priv
= NULL
;
276 fields
[1].in_check_value
= NULL
;
277 fields
[1].in_check_mask
= NULL
;
279 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
280 fields
[2].num_bits
= 1;
281 fields
[2].out_value
= &field2
;
282 fields
[2].out_mask
= NULL
;
283 fields
[2].in_value
= NULL
;
284 fields
[2].in_check_value
= &field2_check_value
;
285 fields
[2].in_check_mask
= &field2_check_mask
;
286 fields
[2].in_handler
= NULL
;
287 fields
[2].in_handler_priv
= NULL
;
289 jtag_add_dr_scan(3, fields
, -1);
291 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
293 ERROR("JTAG error while reading DCSR");
297 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
298 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
300 /* write the register with the value we just read
301 * on this second pass, only the first bit of field0 is guaranteed to be 0)
303 field0_check_mask
= 0x1;
304 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
305 fields
[1].in_value
= NULL
;
307 jtag_add_end_state(TAP_RTI
);
309 jtag_add_dr_scan(3, fields
, -1);
314 int xscale_receive(target_t
*target
, u32
*buffer
, int num_words
)
316 armv4_5_common_t
*armv4_5
= target
->arch_info
;
317 xscale_common_t
*xscale
= armv4_5
->arch_info
;
319 enum tap_state path
[3];
320 scan_field_t fields
[3];
322 u8
*field0
= malloc(num_words
* 1);
323 u8 field0_check_value
= 0x2;
324 u8 field0_check_mask
= 0x6;
325 u32
*field1
= malloc(num_words
* 4);
326 u8 field2_check_value
= 0x0;
327 u8 field2_check_mask
= 0x1;
329 int words_scheduled
= 0;
338 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
339 fields
[0].num_bits
= 3;
340 fields
[0].out_value
= NULL
;
341 fields
[0].out_mask
= NULL
;
342 /* fields[0].in_value = field0; */
343 fields
[0].in_check_value
= &field0_check_value
;
344 fields
[0].in_check_mask
= &field0_check_mask
;
345 fields
[0].in_handler
= NULL
;
346 fields
[0].in_handler_priv
= NULL
;
348 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
349 fields
[1].num_bits
= 32;
350 fields
[1].out_value
= NULL
;
351 fields
[1].out_mask
= NULL
;
352 fields
[1].in_value
= NULL
;
353 fields
[1].in_handler
= NULL
;
354 fields
[1].in_handler_priv
= NULL
;
355 fields
[1].in_check_value
= NULL
;
356 fields
[1].in_check_mask
= NULL
;
358 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
359 fields
[2].num_bits
= 1;
360 fields
[2].out_value
= NULL
;
361 fields
[2].out_mask
= NULL
;
362 fields
[2].in_value
= NULL
;
363 fields
[2].in_check_value
= &field2_check_value
;
364 fields
[2].in_check_mask
= &field2_check_mask
;
365 fields
[2].in_handler
= NULL
;
366 fields
[2].in_handler_priv
= NULL
;
368 jtag_add_end_state(TAP_RTI
);
369 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
370 jtag_add_runtest(1, -1);
372 /* repeat until all words have been collected */
373 while (words_done
< num_words
)
377 for (i
= words_done
; i
< num_words
; i
++)
379 fields
[0].in_value
= &field0
[i
];
380 fields
[1].in_handler
= buf_to_u32_handler
;
381 fields
[1].in_handler_priv
= (u8
*)&field1
[i
];
383 jtag_add_pathmove(3, path
);
384 jtag_add_dr_scan(3, fields
, TAP_RTI
);
388 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
390 ERROR("JTAG error while receiving data from debug handler");
394 /* examine results */
395 for (i
= words_done
; i
< num_words
; i
++)
397 if (!(field0
[0] & 1))
399 /* move backwards if necessary */
401 for (j
= i
; j
< num_words
- 1; j
++)
403 field0
[j
] = field0
[j
+1];
404 field1
[j
] = field1
[j
+1];
409 words_done
+= words_scheduled
;
412 for (i
= 0; i
< num_words
; i
++)
413 *(buffer
++) = buf_get_u32((u8
*)&field1
[i
], 0, 32);
420 int xscale_read_tx(target_t
*target
, int consume
)
422 armv4_5_common_t
*armv4_5
= target
->arch_info
;
423 xscale_common_t
*xscale
= armv4_5
->arch_info
;
424 enum tap_state path
[3];
427 struct timeval timeout
, now
;
429 scan_field_t fields
[3];
431 u8 field0_check_value
= 0x2;
432 u8 field0_check_mask
= 0x6;
433 u8 field2_check_value
= 0x0;
434 u8 field2_check_mask
= 0x1;
436 jtag_add_end_state(TAP_RTI
);
438 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgtx
);
444 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
445 fields
[0].num_bits
= 3;
446 fields
[0].out_value
= NULL
;
447 fields
[0].out_mask
= NULL
;
448 fields
[0].in_value
= &field0_in
;
449 fields
[0].in_check_value
= &field0_check_value
;
450 fields
[0].in_check_mask
= &field0_check_mask
;
451 fields
[0].in_handler
= NULL
;
452 fields
[0].in_handler_priv
= NULL
;
454 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
455 fields
[1].num_bits
= 32;
456 fields
[1].out_value
= NULL
;
457 fields
[1].out_mask
= NULL
;
458 fields
[1].in_value
= xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
;
459 fields
[1].in_handler
= NULL
;
460 fields
[1].in_handler_priv
= NULL
;
461 fields
[1].in_check_value
= NULL
;
462 fields
[1].in_check_mask
= NULL
;
464 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
465 fields
[2].num_bits
= 1;
466 fields
[2].out_value
= NULL
;
467 fields
[2].out_mask
= NULL
;
468 fields
[2].in_value
= NULL
;
469 fields
[2].in_check_value
= &field2_check_value
;
470 fields
[2].in_check_mask
= &field2_check_mask
;
471 fields
[2].in_handler
= NULL
;
472 fields
[2].in_handler_priv
= NULL
;
474 gettimeofday(&timeout
, NULL
);
475 timeval_add_time(&timeout
, 5, 0);
479 /* if we want to consume the register content (i.e. clear TX_READY),
480 * we have to go straight from Capture-DR to Shift-DR
481 * otherwise, we go from Capture-DR to Exit1-DR to Pause-DR
484 jtag_add_pathmove(3, path
);
486 jtag_add_statemove(TAP_PD
);
488 jtag_add_dr_scan(3, fields
, TAP_RTI
);
490 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
492 ERROR("JTAG error while reading TX");
496 gettimeofday(&now
, NULL
);
497 if ((now
.tv_sec
> timeout
.tv_sec
) && (now
.tv_usec
> timeout
.tv_usec
))
499 ERROR("time out reading TX register");
500 return ERROR_TARGET_TIMEOUT
;
502 } while ((!(field0_in
& 1)) && consume
);
504 if (!(field0_in
& 1))
505 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
510 int xscale_write_rx(target_t
*target
)
512 armv4_5_common_t
*armv4_5
= target
->arch_info
;
513 xscale_common_t
*xscale
= armv4_5
->arch_info
;
516 struct timeval timeout
, now
;
518 scan_field_t fields
[3];
521 u8 field0_check_value
= 0x2;
522 u8 field0_check_mask
= 0x6;
524 u8 field2_check_value
= 0x0;
525 u8 field2_check_mask
= 0x1;
527 jtag_add_end_state(TAP_RTI
);
529 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
531 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
532 fields
[0].num_bits
= 3;
533 fields
[0].out_value
= &field0_out
;
534 fields
[0].out_mask
= NULL
;
535 fields
[0].in_value
= &field0_in
;
536 fields
[0].in_check_value
= &field0_check_value
;
537 fields
[0].in_check_mask
= &field0_check_mask
;
538 fields
[0].in_handler
= NULL
;
539 fields
[0].in_handler_priv
= NULL
;
541 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
542 fields
[1].num_bits
= 32;
543 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
;
544 fields
[1].out_mask
= NULL
;
545 fields
[1].in_value
= NULL
;
546 fields
[1].in_handler
= NULL
;
547 fields
[1].in_handler_priv
= NULL
;
548 fields
[1].in_check_value
= NULL
;
549 fields
[1].in_check_mask
= NULL
;
551 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
552 fields
[2].num_bits
= 1;
553 fields
[2].out_value
= &field2
;
554 fields
[2].out_mask
= NULL
;
555 fields
[2].in_value
= NULL
;
556 fields
[2].in_check_value
= &field2_check_value
;
557 fields
[2].in_check_mask
= &field2_check_mask
;
558 fields
[2].in_handler
= NULL
;
559 fields
[2].in_handler_priv
= NULL
;
561 gettimeofday(&timeout
, NULL
);
562 timeval_add_time(&timeout
, 5, 0);
564 /* poll until rx_read is low */
568 jtag_add_dr_scan(3, fields
, TAP_RTI
);
570 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
572 ERROR("JTAG error while writing RX");
576 gettimeofday(&now
, NULL
);
577 if ((now
.tv_sec
> timeout
.tv_sec
) && (now
.tv_usec
> timeout
.tv_usec
))
579 ERROR("time out writing RX register");
580 return ERROR_TARGET_TIMEOUT
;
582 } while (field0_in
& 1);
586 jtag_add_dr_scan(3, fields
, TAP_RTI
);
588 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
590 ERROR("JTAG error while writing RX");
597 /* send count elements of size byte to the debug handler */
598 int xscale_send(target_t
*target
, u8
*buffer
, int count
, int size
)
600 armv4_5_common_t
*armv4_5
= target
->arch_info
;
601 xscale_common_t
*xscale
= armv4_5
->arch_info
;
606 u8 output
[4] = {0, 0, 0, 0};
608 scan_field_t fields
[3];
611 u8 field0_check_value
= 0x2;
612 u8 field0_check_mask
= 0x6;
614 u8 field2_check_value
= 0x0;
615 u8 field2_check_mask
= 0x1;
617 jtag_add_end_state(TAP_RTI
);
619 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dbgrx
);
621 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
622 fields
[0].num_bits
= 3;
623 fields
[0].out_value
= &field0_out
;
624 fields
[0].out_mask
= NULL
;
625 fields
[0].in_value
= &field0_in
;
626 fields
[0].in_check_value
= &field0_check_value
;
627 fields
[0].in_check_mask
= &field0_check_mask
;
628 fields
[0].in_handler
= NULL
;
629 fields
[0].in_handler_priv
= NULL
;
631 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
632 fields
[1].num_bits
= 32;
633 fields
[1].out_value
= output
;
634 fields
[1].out_mask
= NULL
;
635 fields
[1].in_value
= NULL
;
636 fields
[1].in_handler
= NULL
;
637 fields
[1].in_handler_priv
= NULL
;
638 fields
[1].in_check_value
= NULL
;
639 fields
[1].in_check_mask
= NULL
;
641 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
642 fields
[2].num_bits
= 1;
643 fields
[2].out_value
= &field2
;
644 fields
[2].out_mask
= NULL
;
645 fields
[2].in_value
= NULL
;
646 fields
[2].in_check_value
= &field2_check_value
;
647 fields
[2].in_check_mask
= &field2_check_mask
;
648 fields
[2].in_handler
= NULL
;
649 fields
[2].in_handler_priv
= NULL
;
651 while (done_count
++ < count
)
653 /* extract sized element from target-endian buffer, and put it
654 * into little-endian output buffer
659 buf_set_u32(output
, 0, 32, target_buffer_get_u32(target
, buffer
));
662 buf_set_u32(output
, 0, 32, target_buffer_get_u16(target
, buffer
));
668 ERROR("BUG: size neither 4, 2 nor 1");
672 jtag_add_dr_scan(3, fields
, TAP_RTI
);
676 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
678 ERROR("JTAG error while sending data to debug handler");
685 int xscale_send_u32(target_t
*target
, u32 value
)
687 armv4_5_common_t
*armv4_5
= target
->arch_info
;
688 xscale_common_t
*xscale
= armv4_5
->arch_info
;
690 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
691 return xscale_write_rx(target
);
694 int xscale_write_dcsr(target_t
*target
, int hold_rst
, int ext_dbg_brk
)
696 armv4_5_common_t
*armv4_5
= target
->arch_info
;
697 xscale_common_t
*xscale
= armv4_5
->arch_info
;
701 scan_field_t fields
[3];
703 u8 field0_check_value
= 0x2;
704 u8 field0_check_mask
= 0x7;
706 u8 field2_check_value
= 0x0;
707 u8 field2_check_mask
= 0x1;
710 xscale
->hold_rst
= hold_rst
;
712 if (ext_dbg_brk
!= -1)
713 xscale
->external_debug_break
= ext_dbg_brk
;
715 jtag_add_end_state(TAP_RTI
);
716 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.dcsr
);
718 buf_set_u32(&field0
, 1, 1, xscale
->hold_rst
);
719 buf_set_u32(&field0
, 2, 1, xscale
->external_debug_break
);
721 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
722 fields
[0].num_bits
= 3;
723 fields
[0].out_value
= &field0
;
724 fields
[0].out_mask
= NULL
;
725 fields
[0].in_value
= NULL
;
726 fields
[0].in_check_value
= &field0_check_value
;
727 fields
[0].in_check_mask
= &field0_check_mask
;
728 fields
[0].in_handler
= NULL
;
729 fields
[0].in_handler_priv
= NULL
;
731 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
732 fields
[1].num_bits
= 32;
733 fields
[1].out_value
= xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
;
734 fields
[1].out_mask
= NULL
;
735 fields
[1].in_value
= NULL
;
736 fields
[1].in_handler
= NULL
;
737 fields
[1].in_handler_priv
= NULL
;
738 fields
[1].in_check_value
= NULL
;
739 fields
[1].in_check_mask
= NULL
;
741 fields
[2].device
= xscale
->jtag_info
.chain_pos
;
742 fields
[2].num_bits
= 1;
743 fields
[2].out_value
= &field2
;
744 fields
[2].out_mask
= NULL
;
745 fields
[2].in_value
= NULL
;
746 fields
[2].in_check_value
= &field2_check_value
;
747 fields
[2].in_check_mask
= &field2_check_mask
;
748 fields
[2].in_handler
= NULL
;
749 fields
[2].in_handler_priv
= NULL
;
751 jtag_add_dr_scan(3, fields
, -1);
753 if ((retval
= jtag_execute_queue()) != ERROR_OK
)
755 ERROR("JTAG error while writing DCSR");
759 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].dirty
= 0;
760 xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].valid
= 1;
765 /* parity of the number of bits 0 if even; 1 if odd. for 32 bit words */
766 unsigned int parity (unsigned int v
)
773 DEBUG("parity of 0x%x is %i", ov
, (0x6996 >> v
) & 1);
774 return (0x6996 >> v
) & 1;
777 int xscale_load_ic(target_t
*target
, int mini
, u32 va
, u32 buffer
[8])
779 armv4_5_common_t
*armv4_5
= target
->arch_info
;
780 xscale_common_t
*xscale
= armv4_5
->arch_info
;
785 scan_field_t fields
[2];
787 DEBUG("loading miniIC at 0x%8.8x", va
);
789 jtag_add_end_state(TAP_RTI
);
790 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
792 /* CMD is b010 for Main IC and b011 for Mini IC */
794 buf_set_u32(&cmd
, 0, 3, 0x3);
796 buf_set_u32(&cmd
, 0, 3, 0x2);
798 buf_set_u32(&cmd
, 3, 3, 0x0);
800 /* virtual address of desired cache line */
801 buf_set_u32(packet
, 0, 27, va
>> 5);
803 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
804 fields
[0].num_bits
= 6;
805 fields
[0].out_value
= &cmd
;
806 fields
[0].out_mask
= NULL
;
807 fields
[0].in_value
= NULL
;
808 fields
[0].in_check_value
= NULL
;
809 fields
[0].in_check_mask
= NULL
;
810 fields
[0].in_handler
= NULL
;
811 fields
[0].in_handler_priv
= NULL
;
813 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
814 fields
[1].num_bits
= 27;
815 fields
[1].out_value
= packet
;
816 fields
[1].out_mask
= NULL
;
817 fields
[1].in_value
= NULL
;
818 fields
[1].in_check_value
= NULL
;
819 fields
[1].in_check_mask
= NULL
;
820 fields
[1].in_handler
= NULL
;
821 fields
[1].in_handler_priv
= NULL
;
823 jtag_add_dr_scan(2, fields
, -1);
825 fields
[0].num_bits
= 32;
826 fields
[0].out_value
= packet
;
828 fields
[1].num_bits
= 1;
829 fields
[1].out_value
= &cmd
;
831 for (word
= 0; word
< 8; word
++)
833 buf_set_u32(packet
, 0, 32, buffer
[word
]);
834 cmd
= parity(*((u32
*)packet
));
835 jtag_add_dr_scan(2, fields
, -1);
838 jtag_execute_queue();
843 int xscale_invalidate_ic_line(target_t
*target
, u32 va
)
845 armv4_5_common_t
*armv4_5
= target
->arch_info
;
846 xscale_common_t
*xscale
= armv4_5
->arch_info
;
850 scan_field_t fields
[2];
852 jtag_add_end_state(TAP_RTI
);
853 xscale_jtag_set_instr(xscale
->jtag_info
.chain_pos
, xscale
->jtag_info
.ldic
); /* LDIC */
855 /* CMD for invalidate IC line b000, bits [6:4] b000 */
856 buf_set_u32(&cmd
, 0, 6, 0x0);
858 /* virtual address of desired cache line */
859 buf_set_u32(packet
, 0, 27, va
>> 5);
861 fields
[0].device
= xscale
->jtag_info
.chain_pos
;
862 fields
[0].num_bits
= 6;
863 fields
[0].out_value
= &cmd
;
864 fields
[0].out_mask
= NULL
;
865 fields
[0].in_value
= NULL
;
866 fields
[0].in_check_value
= NULL
;
867 fields
[0].in_check_mask
= NULL
;
868 fields
[0].in_handler
= NULL
;
869 fields
[0].in_handler_priv
= NULL
;
871 fields
[1].device
= xscale
->jtag_info
.chain_pos
;
872 fields
[1].num_bits
= 27;
873 fields
[1].out_value
= packet
;
874 fields
[1].out_mask
= NULL
;
875 fields
[1].in_value
= NULL
;
876 fields
[1].in_check_value
= NULL
;
877 fields
[1].in_check_mask
= NULL
;
878 fields
[1].in_handler
= NULL
;
879 fields
[1].in_handler_priv
= NULL
;
881 jtag_add_dr_scan(2, fields
, -1);
886 int xscale_update_vectors(target_t
*target
)
888 armv4_5_common_t
*armv4_5
= target
->arch_info
;
889 xscale_common_t
*xscale
= armv4_5
->arch_info
;
892 u32 low_reset_branch
, high_reset_branch
;
894 for (i
= 1; i
< 8; i
++)
896 /* if there's a static vector specified for this exception, override */
897 if (xscale
->static_high_vectors_set
& (1 << i
))
899 xscale
->high_vectors
[i
] = xscale
->static_high_vectors
[i
];
903 if (target_read_u32(target
, 0xffff0000 + 4*i
, &xscale
->high_vectors
[i
]) != ERROR_OK
)
905 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
910 for (i
= 1; i
< 8; i
++)
912 if (xscale
->static_low_vectors_set
& (1 << i
))
914 xscale
->low_vectors
[i
] = xscale
->static_low_vectors
[i
];
918 if (target_read_u32(target
, 0x0 + 4*i
, &xscale
->low_vectors
[i
]) != ERROR_OK
)
920 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
925 /* calculate branches to debug handler */
926 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
927 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
929 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
930 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
932 /* invalidate and load exception vectors in mini i-cache */
933 xscale_invalidate_ic_line(target
, 0x0);
934 xscale_invalidate_ic_line(target
, 0xffff0000);
936 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
937 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
942 int xscale_arch_state(struct target_s
*target
, char *buf
, int buf_size
)
944 armv4_5_common_t
*armv4_5
= target
->arch_info
;
945 xscale_common_t
*xscale
= armv4_5
->arch_info
;
949 "disabled", "enabled"
952 char *arch_dbg_reason
[] =
954 "", "\n(processor reset)", "\n(trace buffer full)"
957 if (armv4_5
->common_magic
!= ARMV4_5_COMMON_MAGIC
)
959 ERROR("BUG: called for a non-ARMv4/5 target");
963 snprintf(buf
, buf_size
,
964 "target halted in %s state due to %s, current mode: %s\n"
965 "cpsr: 0x%8.8x pc: 0x%8.8x\n"
966 "MMU: %s, D-Cache: %s, I-Cache: %s"
968 armv4_5_state_strings
[armv4_5
->core_state
],
969 target_debug_reason_strings
[target
->debug_reason
],
970 armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)],
971 buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32),
972 buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32),
973 state
[xscale
->armv4_5_mmu
.mmu_enabled
],
974 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
],
975 state
[xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
],
976 arch_dbg_reason
[xscale
->arch_debug_reason
]);
981 enum target_state
xscale_poll(target_t
*target
)
984 armv4_5_common_t
*armv4_5
= target
->arch_info
;
985 xscale_common_t
*xscale
= armv4_5
->arch_info
;
987 if ((target
->state
== TARGET_RUNNING
) || (target
->state
== TARGET_DEBUG_RUNNING
))
989 if ((retval
= xscale_read_tx(target
, 0)) == ERROR_OK
)
991 /* there's data to read from the tx register, we entered debug state */
992 xscale
->handler_running
= 1;
994 /* process debug entry, fetching current mode regs */
995 if ((retval
= xscale_debug_entry(target
)) != ERROR_OK
)
998 /* if target was running, signal that we halted
999 * otherwise we reentered from debug execution */
1000 if (target
->state
== TARGET_RUNNING
)
1001 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1003 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_HALTED
);
1005 target
->state
= TARGET_HALTED
;
1007 else if (retval
!= ERROR_TARGET_RESOURCE_NOT_AVAILABLE
)
1009 ERROR("error while polling TX register");
1014 return target
->state
;
1017 int xscale_debug_entry(target_t
*target
)
1019 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1020 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1022 u32
*buffer
= malloc(4 * 10);
1027 /* clear external dbg break (will be written on next DCSR read) */
1028 xscale
->external_debug_break
= 0;
1029 xscale_read_dcsr(target
);
1031 /* get r0, pc, r1 to r7 and cpsr */
1032 xscale_receive(target
, buffer
, 10);
1034 /* move r0 from buffer to register cache */
1035 buf_set_u32(armv4_5
->core_cache
->reg_list
[0].value
, 0, 32, buffer
[0]);
1036 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1037 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1038 DEBUG("r0: 0x%8.8x", buffer
[0]);
1040 /* move pc from buffer to register cache */
1041 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, buffer
[1]);
1042 armv4_5
->core_cache
->reg_list
[15].dirty
= 1;
1043 armv4_5
->core_cache
->reg_list
[15].valid
= 1;
1044 DEBUG("pc: 0x%8.8x", buffer
[1]);
1046 /* move data from buffer to register cache */
1047 for (i
= 1; i
<= 7; i
++)
1049 buf_set_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32, buffer
[1 + i
]);
1050 armv4_5
->core_cache
->reg_list
[i
].dirty
= 1;
1051 armv4_5
->core_cache
->reg_list
[i
].valid
= 1;
1052 DEBUG("r%i: 0x%8.8x", i
, buffer
[i
+ 1]);
1055 buf_set_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32, buffer
[9]);
1056 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].dirty
= 1;
1057 armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].valid
= 1;
1058 DEBUG("cpsr: 0x%8.8x", buffer
[9]);
1060 armv4_5
->core_mode
= buffer
[9] & 0x1f;
1061 if (armv4_5_mode_to_number(armv4_5
->core_mode
) == -1)
1063 target
->state
= TARGET_UNKNOWN
;
1064 ERROR("cpsr contains invalid mode value - communication failure");
1065 return ERROR_TARGET_FAILURE
;
1067 DEBUG("target entered debug state in %s mode", armv4_5_mode_strings
[armv4_5_mode_to_number(armv4_5
->core_mode
)]);
1069 if (buffer
[9] & 0x20)
1070 armv4_5
->core_state
= ARMV4_5_STATE_THUMB
;
1072 armv4_5
->core_state
= ARMV4_5_STATE_ARM
;
1074 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1075 if ((armv4_5
->core_mode
!= ARMV4_5_MODE_USR
) && (armv4_5
->core_mode
!= ARMV4_5_MODE_SYS
))
1077 xscale_receive(target
, buffer
, 8);
1078 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1079 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).dirty
= 0;
1080 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).valid
= 1;
1084 /* r8 to r14, but no spsr */
1085 xscale_receive(target
, buffer
, 7);
1088 /* move data from buffer to register cache */
1089 for (i
= 8; i
<= 14; i
++)
1091 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).value
, 0, 32, buffer
[i
- 8]);
1092 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).dirty
= 0;
1093 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, i
).valid
= 1;
1096 /* examine debug reason */
1097 xscale_read_dcsr(target
);
1098 moe
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 2, 3);
1100 /* stored PC (for calculating fixup) */
1101 pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1105 case 0x0: /* Processor reset */
1106 target
->debug_reason
= DBG_REASON_DBGRQ
;
1107 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_RESET
;
1110 case 0x1: /* Instruction breakpoint hit */
1111 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1112 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1115 case 0x2: /* Data breakpoint hit */
1116 target
->debug_reason
= DBG_REASON_WATCHPOINT
;
1117 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1120 case 0x3: /* BKPT instruction executed */
1121 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1122 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1125 case 0x4: /* Ext. debug event */
1126 target
->debug_reason
= DBG_REASON_DBGRQ
;
1127 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1130 case 0x5: /* Vector trap occured */
1131 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1132 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_GENERIC
;
1135 case 0x6: /* Trace buffer full break */
1136 target
->debug_reason
= DBG_REASON_DBGRQ
;
1137 xscale
->arch_debug_reason
= XSCALE_DBG_REASON_TB_FULL
;
1140 case 0x7: /* Reserved */
1142 ERROR("Method of Entry is 'Reserved'");
1147 /* apply PC fixup */
1148 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, pc
);
1150 /* on the first debug entry, identify cache type */
1151 if (xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
== -1)
1155 /* read cp15 cache type register */
1156 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
]);
1157 cache_type_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CACHETYPE
].value
, 0, 32);
1159 armv4_5_identify_cache(cache_type_reg
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
1162 /* examine MMU and Cache settings */
1163 /* read cp15 control register */
1164 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
1165 xscale
->cp15_control_reg
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
1166 xscale
->armv4_5_mmu
.mmu_enabled
= (xscale
->cp15_control_reg
& 0x1U
) ? 1 : 0;
1167 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= (xscale
->cp15_control_reg
& 0x4U
) ? 1 : 0;
1168 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= (xscale
->cp15_control_reg
& 0x1000U
) ? 1 : 0;
1173 int xscale_halt(target_t
*target
)
1175 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1176 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1178 DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1180 if (target
->state
== TARGET_HALTED
)
1182 WARNING("target was already halted");
1183 return ERROR_TARGET_ALREADY_HALTED
;
1185 else if (target
->state
== TARGET_UNKNOWN
)
1187 /* this must not happen for a xscale target */
1188 ERROR("target was in unknown state when halt was requested");
1191 else if (target
->state
== TARGET_RESET
)
1193 DEBUG("target->state == TARGET_RESET");
1196 jtag_add_reset(0, -1);
1200 /* assert external dbg break */
1201 xscale
->external_debug_break
= 1;
1202 xscale_read_dcsr(target
);
1204 target
->debug_reason
= DBG_REASON_DBGRQ
;
1210 int xscale_enable_single_step(struct target_s
*target
, u32 next_pc
)
1212 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1213 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1214 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1216 if (xscale
->ibcr0_used
)
1218 breakpoint_t
*ibcr0_bp
= breakpoint_find(target
, buf_get_u32(ibcr0
->value
, 0, 32) & 0xfffffffe);
1222 xscale_unset_breakpoint(target
, ibcr0_bp
);
1226 ERROR("BUG: xscale->ibcr0_used is set, but no breakpoint with that address found");
1231 xscale_set_reg_u32(ibcr0
, next_pc
| 0x1);
1236 int xscale_disable_single_step(struct target_s
*target
)
1238 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1239 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1240 reg_t
*ibcr0
= &xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
];
1242 xscale_set_reg_u32(ibcr0
, 0x0);
1247 int xscale_resume(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
, int debug_execution
)
1249 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1250 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1251 breakpoint_t
*breakpoint
= target
->breakpoints
;
1260 if (target
->state
!= TARGET_HALTED
)
1262 WARNING("target not halted");
1263 return ERROR_TARGET_NOT_HALTED
;
1266 if (!debug_execution
)
1268 target_free_all_working_areas(target
);
1271 /* update vector tables */
1272 xscale_update_vectors(target
);
1274 /* current = 1: continue on current pc, otherwise continue at <address> */
1276 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1278 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1280 /* if we're at the reset vector, we have to simulate the branch */
1281 if (current_pc
== 0x0)
1283 arm_simulate_step(target
, NULL
);
1284 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1287 /* the front-end may request us not to handle breakpoints */
1288 if (handle_breakpoints
)
1290 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1294 /* there's a breakpoint at the current PC, we have to step over it */
1295 DEBUG("unset breakpoint at 0x%8.8x", breakpoint
->address
);
1296 xscale_unset_breakpoint(target
, breakpoint
);
1298 /* calculate PC of next instruction */
1299 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1302 target_read_u32(target
, current_pc
, ¤t_opcode
);
1303 ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1306 DEBUG("enable single-step");
1307 xscale_enable_single_step(target
, next_pc
);
1309 /* restore banked registers */
1310 xscale_restore_context(target
);
1312 /* send resume request (command 0x30 or 0x31)
1313 * clean the trace buffer if it is to be enabled (0x62) */
1314 if (xscale
->trace_buffer_enabled
)
1316 xscale_send_u32(target
, 0x62);
1317 xscale_send_u32(target
, 0x31);
1320 xscale_send_u32(target
, 0x30);
1323 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1324 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1326 for (i
= 7; i
>= 0; i
--)
1329 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1330 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1334 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1335 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1337 /* wait for and process debug entry */
1338 xscale_debug_entry(target
);
1340 DEBUG("disable single-step");
1341 xscale_disable_single_step(target
);
1343 DEBUG("set breakpoint at 0x%8.8x", breakpoint
->address
);
1344 xscale_set_breakpoint(target
, breakpoint
);
1348 /* enable any pending breakpoints and watchpoints */
1349 xscale_enable_breakpoints(target
);
1350 xscale_enable_watchpoints(target
);
1352 /* restore banked registers */
1353 xscale_restore_context(target
);
1355 /* send resume request (command 0x30 or 0x31)
1356 * clean the trace buffer if it is to be enabled (0x62) */
1357 if (xscale
->trace_buffer_enabled
)
1359 xscale_send_u32(target
, 0x62);
1360 xscale_send_u32(target
, 0x31);
1363 xscale_send_u32(target
, 0x30);
1366 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1367 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1369 for (i
= 7; i
>= 0; i
--)
1372 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1373 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1377 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1378 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1380 target
->debug_reason
= DBG_REASON_NOTHALTED
;
1382 if (!debug_execution
)
1384 /* registers are now invalid */
1385 armv4_5_invalidate_core_regs(target
);
1386 target
->state
= TARGET_RUNNING
;
1387 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1391 target
->state
= TARGET_DEBUG_RUNNING
;
1392 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1395 DEBUG("target resumed");
1397 xscale
->handler_running
= 1;
1402 int xscale_step(struct target_s
*target
, int current
, u32 address
, int handle_breakpoints
)
1404 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1405 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1406 breakpoint_t
*breakpoint
= target
->breakpoints
;
1408 u32 current_pc
, next_pc
;
1412 if (target
->state
!= TARGET_HALTED
)
1414 WARNING("target not halted");
1415 return ERROR_TARGET_NOT_HALTED
;
1418 /* current = 1: continue on current pc, otherwise continue at <address> */
1420 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, address
);
1422 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1424 /* if we're at the reset vector, we have to simulate the step */
1425 if (current_pc
== 0x0)
1427 arm_simulate_step(target
, NULL
);
1428 current_pc
= buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32);
1430 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1431 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1436 /* the front-end may request us not to handle breakpoints */
1437 if (handle_breakpoints
)
1438 if ((breakpoint
= breakpoint_find(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32))))
1440 xscale_unset_breakpoint(target
, breakpoint
);
1443 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1445 /* calculate PC of next instruction */
1446 if ((retval
= arm_simulate_step(target
, &next_pc
)) != ERROR_OK
)
1449 target_read_u32(target
, current_pc
, ¤t_opcode
);
1450 ERROR("BUG: couldn't calculate PC of next instruction, current opcode was 0x%8.8x", current_opcode
);
1453 DEBUG("enable single-step");
1454 xscale_enable_single_step(target
, next_pc
);
1456 /* restore banked registers */
1457 xscale_restore_context(target
);
1459 /* send resume request (command 0x30 or 0x31)
1460 * clean the trace buffer if it is to be enabled (0x62) */
1461 if (xscale
->trace_buffer_enabled
)
1463 xscale_send_u32(target
, 0x62);
1464 xscale_send_u32(target
, 0x31);
1467 xscale_send_u32(target
, 0x30);
1470 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1471 DEBUG("writing cpsr with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[ARMV4_5_CPSR
].value
, 0, 32));
1473 for (i
= 7; i
>= 0; i
--)
1476 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1477 DEBUG("writing r%i with value 0x%8.8x", i
, buf_get_u32(armv4_5
->core_cache
->reg_list
[i
].value
, 0, 32));
1481 xscale_send_u32(target
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1482 DEBUG("writing PC with value 0x%8.8x", buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32));
1484 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1486 /* registers are now invalid */
1487 armv4_5_invalidate_core_regs(target
);
1489 /* wait for and process debug entry */
1490 xscale_debug_entry(target
);
1492 DEBUG("disable single-step");
1493 xscale_disable_single_step(target
);
1495 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
1499 xscale_set_breakpoint(target
, breakpoint
);
1502 DEBUG("target stepped");
1508 int xscale_assert_reset(target_t
*target
)
1510 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1511 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1513 DEBUG("target->state: %s", target_state_strings
[target
->state
]);
1515 /* if the handler isn't installed yet, we have to assert TRST, too */
1516 if (!xscale
->handler_installed
)
1518 jtag_add_reset(1, 1);
1521 jtag_add_reset(-1, 1);
1523 /* sleep 1ms, to be sure we fulfill any requirements */
1524 jtag_add_sleep(1000);
1526 target
->state
= TARGET_RESET
;
1532 int xscale_deassert_reset(target_t
*target
)
1534 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1535 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1539 struct stat binary_stat
;
1546 breakpoint_t
*breakpoint
= target
->breakpoints
;
1548 xscale
->ibcr_available
= 2;
1549 xscale
->ibcr0_used
= 0;
1550 xscale
->ibcr1_used
= 0;
1552 xscale
->dbr_available
= 2;
1553 xscale
->dbr0_used
= 0;
1554 xscale
->dbr1_used
= 0;
1556 /* mark all hardware breakpoints as unset */
1559 if (breakpoint
->type
== BKPT_HARD
)
1561 breakpoint
->set
= 0;
1563 breakpoint
= breakpoint
->next
;
1566 if (!xscale
->handler_installed
)
1569 jtag_add_reset(0, -1);
1570 jtag_add_sleep(100000);
1572 /* set Hold reset, Halt mode and Trap Reset */
1573 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 30, 1, 0x1);
1574 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 1, 0x1);
1575 xscale_write_dcsr(target
, 1, 0);
1576 jtag_add_runtest(100, TAP_RTI
);
1577 jtag_execute_queue();
1580 jtag_add_reset(0, 0);
1581 /* wait 150ms; 100ms were not enough */
1582 jtag_add_sleep(150000);
1584 jtag_add_runtest(2030, TAP_RTI
);
1585 jtag_execute_queue();
1587 xscale_write_dcsr(target
, 1, 0);
1588 jtag_execute_queue();
1590 /* TODO: load debug handler */
1591 if (stat("target/xscale/debug_handler.bin", &binary_stat
) == -1)
1593 ERROR("couldn't stat() target/xscale/debug_handler.bin: %s", strerror(errno
));
1597 if (!(binary
= fopen("target/xscale/debug_handler.bin", "r")))
1599 ERROR("couldn't open target/xscale/debug_handler.bin: %s", strerror(errno
));
1603 if ((binary_size
= binary_stat
.st_size
) % 4)
1605 ERROR("debug_handler.bin: size not a multiple of 4");
1609 if (binary_size
> 0x800)
1611 ERROR("debug_handler.bin: larger than 2kb");
1615 binary_size
= CEIL(binary_size
, 32) * 32;
1617 address
= xscale
->handler_address
;
1618 while (binary_size
> 0)
1620 buf_cnt
= fread(buffer
, 4, 8, binary
);
1622 for (i
= 0; i
< buf_cnt
; i
++)
1624 /* convert LE buffer to host-endian u32 */
1625 buffer
[i
] = buf_get_u32((u8
*)(&buffer
[i
]), 0, 32);
1630 for (; buf_cnt
< 8; buf_cnt
++)
1632 buffer
[buf_cnt
] = 0xe1a08008;
1636 /* only load addresses other than the reset vectors */
1637 if ((address
% 0x400) != 0x0)
1639 xscale_load_ic(target
, 1, address
, buffer
);
1642 address
+= buf_cnt
* 4;
1643 binary_size
-= buf_cnt
* 4;
1646 xscale_load_ic(target
, 1, 0x0, xscale
->low_vectors
);
1647 xscale_load_ic(target
, 1, 0xffff0000, xscale
->high_vectors
);
1649 jtag_add_runtest(30, TAP_RTI
);
1651 /* let the target run (should enter debug handler) */
1652 xscale_write_dcsr(target
, 0, 0);
1653 target
->state
= TARGET_RUNNING
;
1655 if ((target
->reset_mode
!= RESET_HALT
) && (target
->reset_mode
!= RESET_INIT
))
1657 jtag_add_sleep(10000);
1659 /* we should have entered debug now */
1660 xscale_debug_entry(target
);
1661 target
->state
= TARGET_HALTED
;
1663 /* the PC is now at 0x0 */
1664 buf_set_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32, 0x0);
1669 jtag_add_reset(0, 0);
1676 int xscale_soft_reset_halt(struct target_s
*target
)
1682 int xscale_read_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
)
1688 int xscale_write_core_reg(struct target_s
*target
, int num
, enum armv4_5_mode mode
, u32 value
)
1694 int xscale_full_context(target_t
*target
)
1696 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1704 if (target
->state
!= TARGET_HALTED
)
1706 WARNING("target not halted");
1707 return ERROR_TARGET_NOT_HALTED
;
1710 buffer
= malloc(4 * 8);
1712 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1713 * we can't enter User mode on an XScale (unpredictable),
1714 * but User shares registers with SYS
1716 for(i
= 1; i
< 7; i
++)
1720 /* check if there are invalid registers in the current mode
1722 for (j
= 0; j
<= 16; j
++)
1724 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
== 0)
1732 /* request banked registers */
1733 xscale_send_u32(target
, 0x0);
1736 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1737 tmp_cpsr
|= 0xc0; /* I/F bits */
1739 /* send CPSR for desired mode */
1740 xscale_send_u32(target
, tmp_cpsr
);
1742 /* get banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1743 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1745 xscale_receive(target
, buffer
, 8);
1746 buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32, buffer
[7]);
1747 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1748 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).valid
= 1;
1752 xscale_receive(target
, buffer
, 7);
1755 /* move data from buffer to register cache */
1756 for (j
= 8; j
<= 14; j
++)
1758 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]);
1759 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1760 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).valid
= 1;
1770 int xscale_restore_context(target_t
*target
)
1772 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1778 if (target
->state
!= TARGET_HALTED
)
1780 WARNING("target not halted");
1781 return ERROR_TARGET_NOT_HALTED
;
1784 /* iterate through processor modes (FIQ, IRQ, SVC, ABT, UND and SYS)
1785 * we can't enter User mode on an XScale (unpredictable),
1786 * but User shares registers with SYS
1788 for(i
= 1; i
< 7; i
++)
1792 /* check if there are invalid registers in the current mode
1794 for (j
= 8; j
<= 14; j
++)
1796 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
== 1)
1800 /* if not USR/SYS, check if the SPSR needs to be written */
1801 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1803 if (ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
== 1)
1811 /* send banked registers */
1812 xscale_send_u32(target
, 0x1);
1815 tmp_cpsr
|= armv4_5_number_to_mode(i
);
1816 tmp_cpsr
|= 0xc0; /* I/F bits */
1818 /* send CPSR for desired mode */
1819 xscale_send_u32(target
, tmp_cpsr
);
1821 /* send banked registers, r8 to r14, and spsr if not in USR/SYS mode */
1822 for (j
= 8; j
<= 14; j
++)
1824 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, j
).value
, 0, 32));
1825 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), j
).dirty
= 0;
1828 if ((armv4_5_number_to_mode(i
) != ARMV4_5_MODE_USR
) && (armv4_5_number_to_mode(i
) != ARMV4_5_MODE_SYS
))
1830 xscale_send_u32(target
, buf_get_u32(ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5
->core_mode
, 16).value
, 0, 32));
1831 ARMV4_5_CORE_REG_MODE(armv4_5
->core_cache
, armv4_5_number_to_mode(i
), 16).dirty
= 0;
1839 int xscale_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1841 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1842 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1846 DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1848 if (target
->state
!= TARGET_HALTED
)
1850 WARNING("target not halted");
1851 return ERROR_TARGET_NOT_HALTED
;
1854 /* sanitize arguments */
1855 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1856 return ERROR_INVALID_ARGUMENTS
;
1858 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1859 return ERROR_TARGET_UNALIGNED_ACCESS
;
1861 /* send memory read request (command 0x1n, n: access size) */
1862 xscale_send_u32(target
, 0x10 | size
);
1864 /* send base address for read request */
1865 xscale_send_u32(target
, address
);
1867 /* send number of requested data words */
1868 xscale_send_u32(target
, count
);
1870 /* receive data from target (count times 32-bit words in host endianness) */
1871 buf32
= malloc(4 * count
);
1872 xscale_receive(target
, buf32
, count
);
1874 /* extract data from host-endian buffer into byte stream */
1875 for (i
= 0; i
< count
; i
++)
1880 target_buffer_set_u32(target
, buffer
, buf32
[i
]);
1884 target_buffer_set_u16(target
, buffer
, buf32
[i
] & 0xffff);
1888 *buffer
++ = buf32
[i
] & 0xff;
1891 ERROR("should never get here");
1898 /* examine DCSR, to see if Sticky Abort (SA) got set */
1899 xscale_read_dcsr(target
);
1900 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1903 xscale_send_u32(target
, 0x60);
1905 return ERROR_TARGET_DATA_ABORT
;
1911 int xscale_write_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
)
1913 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1914 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1916 DEBUG("address: 0x%8.8x, size: 0x%8.8x, count: 0x%8.8x", address
, size
, count
);
1918 if (target
->state
!= TARGET_HALTED
)
1920 WARNING("target not halted");
1921 return ERROR_TARGET_NOT_HALTED
;
1924 /* sanitize arguments */
1925 if (((size
!= 4) && (size
!= 2) && (size
!= 1)) || (count
== 0) || !(buffer
))
1926 return ERROR_INVALID_ARGUMENTS
;
1928 if (((size
== 4) && (address
& 0x3u
)) || ((size
== 2) && (address
& 0x1u
)))
1929 return ERROR_TARGET_UNALIGNED_ACCESS
;
1931 /* send memory write request (command 0x2n, n: access size) */
1932 xscale_send_u32(target
, 0x20 | size
);
1934 /* send base address for read request */
1935 xscale_send_u32(target
, address
);
1937 /* send number of requested data words to be written*/
1938 xscale_send_u32(target
, count
);
1940 /* extract data from host-endian buffer into byte stream */
1942 for (i
= 0; i
< count
; i
++)
1947 value
= target_buffer_get_u32(target
, buffer
);
1948 xscale_send_u32(target
, value
);
1952 value
= target_buffer_get_u16(target
, buffer
);
1953 xscale_send_u32(target
, value
);
1958 xscale_send_u32(target
, value
);
1962 ERROR("should never get here");
1967 xscale_send(target
, buffer
, count
, size
);
1969 /* examine DCSR, to see if Sticky Abort (SA) got set */
1970 xscale_read_dcsr(target
);
1971 if (buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 5, 1) == 1)
1974 xscale_send_u32(target
, 0x60);
1976 return ERROR_TARGET_DATA_ABORT
;
1982 int xscale_bulk_write_memory(target_t
*target
, u32 address
, u32 count
, u8
*buffer
)
1984 xscale_write_memory(target
, address
, 4, count
, buffer
);
1989 u32
xscale_get_ttb(target_t
*target
)
1991 armv4_5_common_t
*armv4_5
= target
->arch_info
;
1992 xscale_common_t
*xscale
= armv4_5
->arch_info
;
1995 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_TTB
]);
1996 ttb
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_TTB
].value
, 0, 32);
2001 void xscale_disable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2003 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2004 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2007 /* read cp15 control register */
2008 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2009 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2012 cp15_control
&= ~0x1U
;
2017 xscale_send_u32(target
, 0x50);
2018 xscale_send_u32(target
, xscale
->cache_clean_address
);
2020 /* invalidate DCache */
2021 xscale_send_u32(target
, 0x51);
2023 cp15_control
&= ~0x4U
;
2028 /* invalidate ICache */
2029 xscale_send_u32(target
, 0x52);
2030 cp15_control
&= ~0x1000U
;
2033 /* write new cp15 control register */
2034 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2036 /* execute cpwait to ensure outstanding operations complete */
2037 xscale_send_u32(target
, 0x53);
2040 void xscale_enable_mmu_caches(target_t
*target
, int mmu
, int d_u_cache
, int i_cache
)
2042 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2043 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2046 /* read cp15 control register */
2047 xscale_get_reg(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
]);
2048 cp15_control
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_CTRL
].value
, 0, 32);
2051 cp15_control
|= 0x1U
;
2054 cp15_control
|= 0x4U
;
2057 cp15_control
|= 0x1000U
;
2059 /* write new cp15 control register */
2060 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_CTRL
], cp15_control
);
2062 /* execute cpwait to ensure outstanding operations complete */
2063 xscale_send_u32(target
, 0x53);
2066 int xscale_set_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2068 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2069 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2071 if (target
->state
!= TARGET_HALTED
)
2073 WARNING("target not halted");
2074 return ERROR_TARGET_NOT_HALTED
;
2077 if (xscale
->force_hw_bkpts
)
2078 breakpoint
->type
= BKPT_HARD
;
2080 if (breakpoint
->set
)
2082 WARNING("breakpoint already set");
2086 if (breakpoint
->type
== BKPT_HARD
)
2088 u32 value
= breakpoint
->address
| 1;
2089 if (!xscale
->ibcr0_used
)
2091 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], value
);
2092 xscale
->ibcr0_used
= 1;
2093 breakpoint
->set
= 1; /* breakpoint set on first breakpoint register */
2095 else if (!xscale
->ibcr1_used
)
2097 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], value
);
2098 xscale
->ibcr1_used
= 1;
2099 breakpoint
->set
= 2; /* breakpoint set on second breakpoint register */
2103 ERROR("BUG: no hardware comparator available");
2107 else if (breakpoint
->type
== BKPT_SOFT
)
2109 if (breakpoint
->length
== 4)
2111 /* keep the original instruction in target endianness */
2112 target
->type
->read_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2113 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2114 target_write_u32(target
, breakpoint
->address
, xscale
->arm_bkpt
);
2118 /* keep the original instruction in target endianness */
2119 target
->type
->read_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2120 /* write the original instruction in target endianness (arm7_9->arm_bkpt is host endian) */
2121 target_write_u32(target
, breakpoint
->address
, xscale
->thumb_bkpt
);
2123 breakpoint
->set
= 1;
2130 int xscale_add_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2132 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2133 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2135 if (target
->state
!= TARGET_HALTED
)
2137 WARNING("target not halted");
2138 return ERROR_TARGET_NOT_HALTED
;
2141 if (xscale
->force_hw_bkpts
)
2143 DEBUG("forcing use of hardware breakpoint at address 0x%8.8x", breakpoint
->address
);
2144 breakpoint
->type
= BKPT_HARD
;
2147 if ((breakpoint
->type
== BKPT_HARD
) && (xscale
->ibcr_available
< 1))
2149 INFO("no breakpoint unit available for hardware breakpoint");
2150 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2154 xscale
->ibcr_available
--;
2157 if ((breakpoint
->length
!= 2) && (breakpoint
->length
!= 4))
2159 INFO("only breakpoints of two (Thumb) or four (ARM) bytes length supported");
2160 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2166 int xscale_unset_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2168 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2169 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2171 if (target
->state
!= TARGET_HALTED
)
2173 WARNING("target not halted");
2174 return ERROR_TARGET_NOT_HALTED
;
2177 if (!breakpoint
->set
)
2179 WARNING("breakpoint not set");
2183 if (breakpoint
->type
== BKPT_HARD
)
2185 if (breakpoint
->set
== 1)
2187 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR0
], 0x0);
2188 xscale
->ibcr0_used
= 0;
2190 else if (breakpoint
->set
== 2)
2192 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_IBCR1
], 0x0);
2193 xscale
->ibcr1_used
= 0;
2195 breakpoint
->set
= 0;
2199 /* restore original instruction (kept in target endianness) */
2200 if (breakpoint
->length
== 4)
2202 target
->type
->write_memory(target
, breakpoint
->address
, 4, 1, breakpoint
->orig_instr
);
2206 target
->type
->write_memory(target
, breakpoint
->address
, 2, 1, breakpoint
->orig_instr
);
2208 breakpoint
->set
= 0;
2214 int xscale_remove_breakpoint(struct target_s
*target
, breakpoint_t
*breakpoint
)
2216 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2217 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2219 if (target
->state
!= TARGET_HALTED
)
2221 WARNING("target not halted");
2222 return ERROR_TARGET_NOT_HALTED
;
2225 if (breakpoint
->set
)
2227 xscale_unset_breakpoint(target
, breakpoint
);
2230 if (breakpoint
->type
== BKPT_HARD
)
2231 xscale
->ibcr_available
++;
2236 int xscale_set_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2238 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2239 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2241 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2242 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2244 if (target
->state
!= TARGET_HALTED
)
2246 WARNING("target not halted");
2247 return ERROR_TARGET_NOT_HALTED
;
2250 xscale_get_reg(dbcon
);
2252 switch (watchpoint
->rw
)
2264 ERROR("BUG: watchpoint->rw neither read, write nor access");
2267 if (!xscale
->dbr0_used
)
2269 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR0
], watchpoint
->address
);
2270 dbcon_value
|= enable
;
2271 xscale_set_reg_u32(dbcon
, dbcon_value
);
2272 watchpoint
->set
= 1;
2273 xscale
->dbr0_used
= 1;
2275 else if (!xscale
->dbr1_used
)
2277 xscale_set_reg_u32(&xscale
->reg_cache
->reg_list
[XSCALE_DBR1
], watchpoint
->address
);
2278 dbcon_value
|= enable
<< 2;
2279 xscale_set_reg_u32(dbcon
, dbcon_value
);
2280 watchpoint
->set
= 2;
2281 xscale
->dbr1_used
= 1;
2285 ERROR("BUG: no hardware comparator available");
2292 int xscale_add_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2294 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2295 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2297 if (target
->state
!= TARGET_HALTED
)
2299 WARNING("target not halted");
2300 return ERROR_TARGET_NOT_HALTED
;
2303 if (xscale
->dbr_available
< 1)
2305 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2308 if ((watchpoint
->length
!= 1) && (watchpoint
->length
!= 2) && (watchpoint
->length
!= 4))
2310 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
2313 xscale
->dbr_available
--;
2318 int xscale_unset_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2320 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2321 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2322 reg_t
*dbcon
= &xscale
->reg_cache
->reg_list
[XSCALE_DBCON
];
2323 u32 dbcon_value
= buf_get_u32(dbcon
->value
, 0, 32);
2325 if (target
->state
!= TARGET_HALTED
)
2327 WARNING("target not halted");
2328 return ERROR_TARGET_NOT_HALTED
;
2331 if (!watchpoint
->set
)
2333 WARNING("breakpoint not set");
2337 if (watchpoint
->set
== 1)
2339 dbcon_value
&= ~0x3;
2340 xscale_set_reg_u32(dbcon
, dbcon_value
);
2341 xscale
->dbr0_used
= 0;
2343 else if (watchpoint
->set
== 2)
2345 dbcon_value
&= ~0xc;
2346 xscale_set_reg_u32(dbcon
, dbcon_value
);
2347 xscale
->dbr1_used
= 0;
2349 watchpoint
->set
= 0;
2354 int xscale_remove_watchpoint(struct target_s
*target
, watchpoint_t
*watchpoint
)
2356 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2357 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2359 if (target
->state
!= TARGET_HALTED
)
2361 WARNING("target not halted");
2362 return ERROR_TARGET_NOT_HALTED
;
2365 if (watchpoint
->set
)
2367 xscale_unset_watchpoint(target
, watchpoint
);
2370 xscale
->dbr_available
++;
2375 void xscale_enable_watchpoints(struct target_s
*target
)
2377 watchpoint_t
*watchpoint
= target
->watchpoints
;
2381 if (watchpoint
->set
== 0)
2382 xscale_set_watchpoint(target
, watchpoint
);
2383 watchpoint
= watchpoint
->next
;
2387 void xscale_enable_breakpoints(struct target_s
*target
)
2389 breakpoint_t
*breakpoint
= target
->breakpoints
;
2391 /* set any pending breakpoints */
2394 if (breakpoint
->set
== 0)
2395 xscale_set_breakpoint(target
, breakpoint
);
2396 breakpoint
= breakpoint
->next
;
2400 int xscale_get_reg(reg_t
*reg
)
2402 xscale_reg_t
*arch_info
= reg
->arch_info
;
2403 target_t
*target
= arch_info
->target
;
2404 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2405 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2407 /* DCSR, TX and RX are accessible via JTAG */
2408 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2410 return xscale_read_dcsr(arch_info
->target
);
2412 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2414 /* 1 = consume register content */
2415 return xscale_read_tx(arch_info
->target
, 1);
2417 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2419 /* can't read from RX register (host -> debug handler) */
2422 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2424 /* can't (explicitly) read from TXRXCTRL register */
2427 else /* Other DBG registers have to be transfered by the debug handler */
2429 /* send CP read request (command 0x40) */
2430 xscale_send_u32(target
, 0x40);
2432 /* send CP register number */
2433 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2435 /* read register value */
2436 xscale_read_tx(target
, 1);
2437 buf_cpy(xscale
->reg_cache
->reg_list
[XSCALE_TX
].value
, reg
->value
, 32);
2446 int xscale_set_reg(reg_t
*reg
, u8
* buf
)
2448 xscale_reg_t
*arch_info
= reg
->arch_info
;
2449 target_t
*target
= arch_info
->target
;
2450 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2451 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2452 u32 value
= buf_get_u32(buf
, 0, 32);
2454 /* DCSR, TX and RX are accessible via JTAG */
2455 if (strcmp(reg
->name
, "XSCALE_DCSR") == 0)
2457 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32, value
);
2458 return xscale_write_dcsr(arch_info
->target
, -1, -1);
2460 else if (strcmp(reg
->name
, "XSCALE_RX") == 0)
2462 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_RX
].value
, 0, 32, value
);
2463 return xscale_write_rx(arch_info
->target
);
2465 else if (strcmp(reg
->name
, "XSCALE_TX") == 0)
2467 /* can't write to TX register (debug-handler -> host) */
2470 else if (strcmp(reg
->name
, "XSCALE_TXRXCTRL") == 0)
2472 /* can't (explicitly) write to TXRXCTRL register */
2475 else /* Other DBG registers have to be transfered by the debug handler */
2477 /* send CP write request (command 0x41) */
2478 xscale_send_u32(target
, 0x41);
2480 /* send CP register number */
2481 xscale_send_u32(target
, arch_info
->dbg_handler_number
);
2483 /* send CP register value */
2484 xscale_send_u32(target
, value
);
2485 buf_set_u32(reg
->value
, 0, 32, value
);
2491 /* convenience wrapper to access XScale specific registers */
2492 int xscale_set_reg_u32(reg_t
*reg
, u32 value
)
2496 buf_set_u32(buf
, 0, 32, value
);
2498 return xscale_set_reg(reg
, buf
);
2501 int xscale_write_dcsr_sw(target_t
*target
, u32 value
)
2503 /* get pointers to arch-specific information */
2504 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2505 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2506 reg_t
*dcsr
= &xscale
->reg_cache
->reg_list
[XSCALE_DCSR
];
2507 xscale_reg_t
*dcsr_arch_info
= dcsr
->arch_info
;
2509 /* send CP write request (command 0x41) */
2510 xscale_send_u32(target
, 0x41);
2512 /* send CP register number */
2513 xscale_send_u32(target
, dcsr_arch_info
->dbg_handler_number
);
2515 /* send CP register value */
2516 xscale_send_u32(target
, value
);
2517 buf_set_u32(dcsr
->value
, 0, 32, value
);
2522 void xscale_build_reg_cache(target_t
*target
)
2524 /* get pointers to arch-specific information */
2525 armv4_5_common_t
*armv4_5
= target
->arch_info
;
2526 xscale_common_t
*xscale
= armv4_5
->arch_info
;
2528 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
2529 xscale_reg_t
*arch_info
= malloc(sizeof(xscale_reg_arch_info
));
2531 int num_regs
= sizeof(xscale_reg_arch_info
) / sizeof(xscale_reg_t
);
2533 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
2534 armv4_5
->core_cache
= (*cache_p
);
2536 /* register a register arch-type for XScale dbg registers only once */
2537 if (xscale_reg_arch_type
== -1)
2538 xscale_reg_arch_type
= register_reg_arch_type(xscale_get_reg
, xscale_set_reg
);
2540 (*cache_p
)->next
= malloc(sizeof(reg_cache_t
));
2541 cache_p
= &(*cache_p
)->next
;
2543 /* fill in values for the xscale reg cache */
2544 (*cache_p
)->name
= "XScale registers";
2545 (*cache_p
)->next
= NULL
;
2546 (*cache_p
)->reg_list
= malloc(num_regs
* sizeof(reg_t
));
2547 (*cache_p
)->num_regs
= num_regs
;
2549 for (i
= 0; i
< num_regs
; i
++)
2551 (*cache_p
)->reg_list
[i
].name
= xscale_reg_list
[i
];
2552 (*cache_p
)->reg_list
[i
].value
= calloc(4, 1);
2553 (*cache_p
)->reg_list
[i
].dirty
= 0;
2554 (*cache_p
)->reg_list
[i
].valid
= 0;
2555 (*cache_p
)->reg_list
[i
].size
= 32;
2556 (*cache_p
)->reg_list
[i
].bitfield_desc
= NULL
;
2557 (*cache_p
)->reg_list
[i
].num_bitfields
= 0;
2558 (*cache_p
)->reg_list
[i
].arch_info
= &arch_info
[i
];
2559 (*cache_p
)->reg_list
[i
].arch_type
= xscale_reg_arch_type
;
2560 arch_info
[i
] = xscale_reg_arch_info
[i
];
2561 arch_info
[i
].target
= target
;
2564 xscale
->reg_cache
= (*cache_p
);
2567 int xscale_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
2569 if (startup_mode
!= DAEMON_RESET
)
2571 ERROR("XScale target requires a reset");
2572 ERROR("Reset target to enable debug");
2584 int xscale_init_arch_info(target_t
*target
, xscale_common_t
*xscale
, int chain_pos
, char *variant
)
2586 armv4_5_common_t
*armv4_5
;
2587 u32 high_reset_branch
, low_reset_branch
;
2590 armv4_5
= &xscale
->armv4_5_common
;
2592 /* store architecture specfic data (none so far) */
2593 xscale
->arch_info
= NULL
;
2594 xscale
->common_magic
= XSCALE_COMMON_MAGIC
;
2596 /* remember the variant (PXA25x, PXA27x, IXP42x, ...) */
2597 xscale
->variant
= strdup(variant
);
2599 /* prepare JTAG information for the new target */
2600 xscale
->jtag_info
.chain_pos
= chain_pos
;
2601 jtag_register_event_callback(xscale_jtag_callback
, target
);
2603 xscale
->jtag_info
.dbgrx
= 0x02;
2604 xscale
->jtag_info
.dbgtx
= 0x10;
2605 xscale
->jtag_info
.dcsr
= 0x09;
2606 xscale
->jtag_info
.ldic
= 0x07;
2608 if ((strcmp(xscale
->variant
, "pxa250") == 0) ||
2609 (strcmp(xscale
->variant
, "pxa255") == 0) ||
2610 (strcmp(xscale
->variant
, "pxa26x") == 0))
2612 xscale
->jtag_info
.ir_length
= 5;
2614 else if ((strcmp(xscale
->variant
, "pxa27x") == 0) ||
2615 (strcmp(xscale
->variant
, "ixp42x") == 0) ||
2616 (strcmp(xscale
->variant
, "ixp45x") == 0) ||
2617 (strcmp(xscale
->variant
, "ixp46x") == 0))
2619 xscale
->jtag_info
.ir_length
= 7;
2622 /* the debug handler isn't installed (and thus not running) at this time */
2623 xscale
->handler_installed
= 0;
2624 xscale
->handler_running
= 0;
2625 xscale
->handler_address
= 0xfe000800;
2627 /* clear the vectors we keep locally for reference */
2628 memset(xscale
->low_vectors
, 0, sizeof(xscale
->low_vectors
));
2629 memset(xscale
->high_vectors
, 0, sizeof(xscale
->high_vectors
));
2631 /* no user-specified vectors have been configured yet */
2632 xscale
->static_low_vectors_set
= 0x0;
2633 xscale
->static_high_vectors_set
= 0x0;
2635 /* calculate branches to debug handler */
2636 low_reset_branch
= (xscale
->handler_address
+ 0x20 - 0x0 - 0x8) >> 2;
2637 high_reset_branch
= (xscale
->handler_address
+ 0x20 - 0xffff0000 - 0x8) >> 2;
2639 xscale
->low_vectors
[0] = ARMV4_5_B((low_reset_branch
& 0xffffff), 0);
2640 xscale
->high_vectors
[0] = ARMV4_5_B((high_reset_branch
& 0xffffff), 0);
2642 for (i
= 1; i
<= 7; i
++)
2644 xscale
->low_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
2645 xscale
->high_vectors
[i
] = ARMV4_5_B(0xfffffe, 0);
2648 /* 64kB aligned region used for DCache cleaning */
2649 xscale
->cache_clean_address
= 0xfffe0000;
2651 xscale
->hold_rst
= 0;
2652 xscale
->external_debug_break
= 0;
2654 xscale
->force_hw_bkpts
= 1;
2656 xscale
->ibcr_available
= 2;
2657 xscale
->ibcr0_used
= 0;
2658 xscale
->ibcr1_used
= 0;
2660 xscale
->dbr_available
= 2;
2661 xscale
->dbr0_used
= 0;
2662 xscale
->dbr1_used
= 0;
2664 xscale
->arm_bkpt
= ARMV5_BKPT(0x0);
2665 xscale
->thumb_bkpt
= ARMV5_T_BKPT(0x0) & 0xffff;
2667 xscale
->vector_catch
= 0x1;
2669 xscale
->trace_buffer_enabled
= 0;
2670 xscale
->trace_buffer_fill
= 0;
2672 /* prepare ARMv4/5 specific information */
2673 armv4_5
->arch_info
= xscale
;
2674 armv4_5
->read_core_reg
= xscale_read_core_reg
;
2675 armv4_5
->write_core_reg
= xscale_write_core_reg
;
2676 armv4_5
->full_context
= xscale_full_context
;
2678 armv4_5_init_arch_info(target
, armv4_5
);
2680 xscale
->armv4_5_mmu
.armv4_5_cache
.ctype
= -1;
2681 xscale
->armv4_5_mmu
.get_ttb
= xscale_get_ttb
;
2682 xscale
->armv4_5_mmu
.read_memory
= xscale_read_memory
;
2683 xscale
->armv4_5_mmu
.write_memory
= xscale_write_memory
;
2684 xscale
->armv4_5_mmu
.disable_mmu_caches
= xscale_disable_mmu_caches
;
2685 xscale
->armv4_5_mmu
.enable_mmu_caches
= xscale_enable_mmu_caches
;
2686 xscale
->armv4_5_mmu
.has_tiny_pages
= 1;
2687 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
2692 /* target xscale <endianess> <startup_mode> <chain_pos> <variant> */
2693 int xscale_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
)
2696 char *variant
= NULL
;
2697 xscale_common_t
*xscale
= malloc(sizeof(xscale_common_t
));
2701 ERROR("'target xscale' requires four arguments: <endianess> <startup_mode> <chain_pos> <variant>");
2705 chain_pos
= strtoul(args
[3], NULL
, 0);
2709 xscale_init_arch_info(target
, xscale
, chain_pos
, variant
);
2710 xscale_build_reg_cache(target
);
2715 int xscale_handle_debug_handler_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2717 target_t
*target
= NULL
;
2718 armv4_5_common_t
*armv4_5
;
2719 xscale_common_t
*xscale
;
2721 u32 handler_address
;
2725 ERROR("'xscale debug_handler <target#> <address>' command takes two required operands");
2729 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
2731 ERROR("no target '%s' configured", args
[0]);
2735 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2737 command_print(cmd_ctx
, "target isn't an ARM920t target");
2741 handler_address
= strtoul(args
[1], NULL
, 0);
2743 if (((handler_address
>= 0x800) && (handler_address
<= 0x1fef800)) ||
2744 ((handler_address
>= 0xfe000800) && (handler_address
<= 0xfffff800)))
2746 xscale
->handler_address
= handler_address
;
2750 ERROR("xscale debug_handler <address> must be between 0x800 and 0x1fef800 or between 0xfe000800 and 0xfffff800");
2756 int xscale_handle_cache_clean_address_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2758 target_t
*target
= NULL
;
2759 armv4_5_common_t
*armv4_5
;
2760 xscale_common_t
*xscale
;
2762 u32 cache_clean_address
;
2766 ERROR("'xscale cache_clean_address <target#> <address>' command takes two required operands");
2770 if ((target
= get_target_by_num(strtoul(args
[0], NULL
, 0))) == NULL
)
2772 ERROR("no target '%s' configured", args
[0]);
2776 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2778 command_print(cmd_ctx
, "target isn't an XScale target");
2782 cache_clean_address
= strtoul(args
[1], NULL
, 0);
2784 if (cache_clean_address
& 0xffff)
2786 ERROR("xscale cache_clean_address <address> must be 64kb aligned");
2790 xscale
->cache_clean_address
= cache_clean_address
;
2796 int xscale_handle_cache_info_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2798 target_t
*target
= get_current_target(cmd_ctx
);
2799 armv4_5_common_t
*armv4_5
;
2800 xscale_common_t
*xscale
;
2802 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2804 command_print(cmd_ctx
, "target isn't an XScale target");
2808 return armv4_5_handle_cache_info_command(cmd_ctx
, &xscale
->armv4_5_mmu
.armv4_5_cache
);
2811 int xscale_handle_virt2phys_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2813 target_t
*target
= get_current_target(cmd_ctx
);
2814 armv4_5_common_t
*armv4_5
;
2815 xscale_common_t
*xscale
;
2817 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2819 command_print(cmd_ctx
, "target isn't an XScale target");
2823 if (target
->state
!= TARGET_HALTED
)
2825 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
2829 return armv4_5_mmu_handle_virt2phys_command(cmd_ctx
, cmd
, args
, argc
, target
, &xscale
->armv4_5_mmu
);
2832 int xscale_handle_mmu_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2834 target_t
*target
= get_current_target(cmd_ctx
);
2835 armv4_5_common_t
*armv4_5
;
2836 xscale_common_t
*xscale
;
2838 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2840 command_print(cmd_ctx
, "target isn't an XScale target");
2844 if (target
->state
!= TARGET_HALTED
)
2846 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
2852 if (strcmp("enable", args
[0]) == 0)
2854 xscale_enable_mmu_caches(target
, 1, 0, 0);
2855 xscale
->armv4_5_mmu
.mmu_enabled
= 1;
2857 else if (strcmp("disable", args
[0]) == 0)
2859 xscale_disable_mmu_caches(target
, 1, 0, 0);
2860 xscale
->armv4_5_mmu
.mmu_enabled
= 0;
2864 command_print(cmd_ctx
, "mmu %s", (xscale
->armv4_5_mmu
.mmu_enabled
) ? "enabled" : "disabled");
2869 int xscale_handle_idcache_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2871 target_t
*target
= get_current_target(cmd_ctx
);
2872 armv4_5_common_t
*armv4_5
;
2873 xscale_common_t
*xscale
;
2874 int icache
= 0, dcache
= 0;
2876 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2878 command_print(cmd_ctx
, "target isn't an XScale target");
2882 if (target
->state
!= TARGET_HALTED
)
2884 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
2888 if (strcmp(cmd
, "icache") == 0)
2890 else if (strcmp(cmd
, "dcache") == 0)
2895 if (strcmp("enable", args
[0]) == 0)
2897 xscale_enable_mmu_caches(target
, 0, dcache
, icache
);
2900 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 1;
2902 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 1;
2904 else if (strcmp("disable", args
[0]) == 0)
2906 xscale_disable_mmu_caches(target
, 0, dcache
, icache
);
2909 xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
= 0;
2911 xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
= 0;
2916 command_print(cmd_ctx
, "icache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.i_cache_enabled
) ? "enabled" : "disabled");
2919 command_print(cmd_ctx
, "dcache %s", (xscale
->armv4_5_mmu
.armv4_5_cache
.d_u_cache_enabled
) ? "enabled" : "disabled");
2924 int xscale_handle_vector_catch_command(command_context_t
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2926 target_t
*target
= get_current_target(cmd_ctx
);
2927 armv4_5_common_t
*armv4_5
;
2928 xscale_common_t
*xscale
;
2930 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2932 command_print(cmd_ctx
, "target isn't an XScale target");
2938 command_print(cmd_ctx
, "usage: xscale vector_catch [mask]");
2942 xscale
->vector_catch
= strtoul(args
[0], NULL
, 0);
2943 buf_set_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 16, 8, xscale
->vector_catch
);
2944 xscale_write_dcsr(target
, -1, -1);
2947 command_print(cmd_ctx
, "vector catch mask: 0x%2.2x", xscale
->vector_catch
);
2952 int xscale_handle_force_hw_bkpts_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2954 target_t
*target
= get_current_target(cmd_ctx
);
2955 armv4_5_common_t
*armv4_5
;
2956 xscale_common_t
*xscale
;
2958 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2960 command_print(cmd_ctx
, "target isn't an XScale target");
2964 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
2966 xscale
->force_hw_bkpts
= 1;
2968 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
2970 xscale
->force_hw_bkpts
= 0;
2974 command_print(cmd_ctx
, "usage: xscale force_hw_bkpts <enable|disable>");
2977 command_print(cmd_ctx
, "force hardware breakpoints %s", (xscale
->force_hw_bkpts
) ? "enabled" : "disabled");
2982 int xscale_handle_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
2984 target_t
*target
= get_current_target(cmd_ctx
);
2985 armv4_5_common_t
*armv4_5
;
2986 xscale_common_t
*xscale
;
2989 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
2991 command_print(cmd_ctx
, "target isn't an XScale target");
2995 if (target
->state
!= TARGET_HALTED
)
2997 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3001 if ((argc
>= 1) && (strcmp("enable", args
[0]) == 0))
3003 xscale
->trace_buffer_enabled
= 1;
3005 else if ((argc
>= 1) && (strcmp("disable", args
[0]) == 0))
3007 xscale
->trace_buffer_enabled
= 0;
3010 if ((argc
>= 2) && (strcmp("fill", args
[1]) == 0))
3012 xscale
->trace_buffer_fill
= 1;
3014 else if ((argc
>= 2) && (strcmp("wrap", args
[1]) == 0))
3016 xscale
->trace_buffer_fill
= 0;
3019 command_print(cmd_ctx
, "trace buffer %s (%s)",
3020 (xscale
->trace_buffer_enabled
) ? "enabled" : "disabled",
3021 (xscale
->trace_buffer_fill
) ? "fill" : "wrap");
3023 dcsr_value
= buf_get_u32(xscale
->reg_cache
->reg_list
[XSCALE_DCSR
].value
, 0, 32);
3024 if (xscale
->trace_buffer_fill
)
3025 xscale_write_dcsr_sw(target
, (dcsr_value
& 0xfffffffc) | 2);
3027 xscale_write_dcsr_sw(target
, dcsr_value
& 0xfffffffc);
3032 int xscale_handle_dump_trace_buffer_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
)
3034 target_t
*target
= get_current_target(cmd_ctx
);
3035 armv4_5_common_t
*armv4_5
;
3036 xscale_common_t
*xscale
;
3037 u32 trace_buffer
[258];
3038 int is_address
[256];
3041 if (xscale_get_arch_pointers(target
, &armv4_5
, &xscale
) != ERROR_OK
)
3043 command_print(cmd_ctx
, "target isn't an XScale target");
3047 if (target
->state
!= TARGET_HALTED
)
3049 command_print(cmd_ctx
, "target must be stopped for \"%s\" command", cmd
);
3053 /* send read trace buffer command (command 0x61) */
3054 xscale_send_u32(target
, 0x61);
3056 /* receive trace buffer content */
3057 xscale_receive(target
, trace_buffer
, 258);
3059 for (i
= 255; i
>= 0; i
--)
3062 if (((trace_buffer
[i
] & 0xf0) == 0x90) ||
3063 ((trace_buffer
[i
] & 0xf0) == 0xd0))
3066 is_address
[--i
] = 1;
3068 is_address
[--i
] = 1;
3070 is_address
[--i
] = 1;
3072 is_address
[--i
] = 1;
3076 for (i
= 0; i
< 256; i
++)
3079 command_print(cmd_ctx
, "0x%2.2x 0x%2.2x 0x%2.2x 0x%2.2x 0x%2.2x 0x%2.2x 0x%2.2x 0x%2.2x",
3080 trace_buffer
[i
+ 0], trace_buffer
[i
+ 1], trace_buffer
[i
+ 2], trace_buffer
[i
+ 3],
3081 trace_buffer
[i
+ 4], trace_buffer
[i
+ 5], trace_buffer
[i
+ 6], trace_buffer
[i
+ 6]
3087 command_print(cmd_ctx
, "address: 0x%2.2x%2.2x%2.2x%2.2x", trace_buffer
[i
], trace_buffer
[i
+1], trace_buffer
[i
+2], trace_buffer
[i
+3]);
3092 switch ((trace_buffer
[i
] & 0xf0) >> 4)
3095 command_print(cmd_ctx
, "0x%2.2x: reset exception", trace_buffer
[i
]);
3098 command_print(cmd_ctx
, "0x%2.2x: undef exception", trace_buffer
[i
]);
3101 command_print(cmd_ctx
, "0x%2.2x: swi exception", trace_buffer
[i
]);
3104 command_print(cmd_ctx
, "0x%2.2x: pabort exception", trace_buffer
[i
]);
3107 command_print(cmd_ctx
, "0x%2.2x: dabort exception", trace_buffer
[i
]);
3110 command_print(cmd_ctx
, "0x%2.2x: invalid", trace_buffer
[i
]);
3113 command_print(cmd_ctx
, "0x%2.2x: irq exception", trace_buffer
[i
]);
3116 command_print(cmd_ctx
, "0x%2.2x: fiq exception", trace_buffer
[i
]);
3119 command_print(cmd_ctx
, "0x%2.2x: direct branch", trace_buffer
[i
]);
3122 command_print(cmd_ctx
, "0x%2.2x: indirect branch", trace_buffer
[i
]);
3125 command_print(cmd_ctx
, "0x%2.2x: invalid", trace_buffer
[i
]);
3128 command_print(cmd_ctx
, "0x%2.2x: invalid", trace_buffer
[i
]);
3131 command_print(cmd_ctx
, "0x%2.2x: checkpointed direct branch", trace_buffer
[i
]);
3134 command_print(cmd_ctx
, "0x%2.2x: checkpointed indirect branch", trace_buffer
[i
]);
3137 command_print(cmd_ctx
, "0x%2.2x: invalid", trace_buffer
[i
]);
3140 command_print(cmd_ctx
, "0x%2.2x: rollover", trace_buffer
[i
]);
3146 command_print(cmd_ctx
, "chkpt0: 0x%8.8x, chkpt1: 0x%8.8x", trace_buffer
[256], trace_buffer
[257]);
3151 int xscale_register_commands(struct command_context_s
*cmd_ctx
)
3153 command_t
*xscale_cmd
;
3155 xscale_cmd
= register_command(cmd_ctx
, NULL
, "xscale", NULL
, COMMAND_ANY
, "xscale specific commands");
3157 register_command(cmd_ctx
, xscale_cmd
, "debug_handler", xscale_handle_debug_handler_command
, COMMAND_CONFIG
, NULL
);
3158 register_command(cmd_ctx
, xscale_cmd
, "cache_clean_address", xscale_handle_cache_clean_address_command
, COMMAND_ANY
, NULL
);
3160 register_command(cmd_ctx
, xscale_cmd
, "cache_info", xscale_handle_cache_info_command
, COMMAND_EXEC
, NULL
);
3161 register_command(cmd_ctx
, xscale_cmd
, "virt2phys", xscale_handle_virt2phys_command
, COMMAND_EXEC
, NULL
);
3162 register_command(cmd_ctx
, xscale_cmd
, "mmu", xscale_handle_mmu_command
, COMMAND_EXEC
, "['enable'|'disable'] the MMU");
3163 register_command(cmd_ctx
, xscale_cmd
, "icache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the ICache");
3164 register_command(cmd_ctx
, xscale_cmd
, "dcache", xscale_handle_idcache_command
, COMMAND_EXEC
, "['enable'|'disable'] the DCache");
3166 register_command(cmd_ctx
, xscale_cmd
, "vector_catch", xscale_handle_idcache_command
, COMMAND_EXEC
, "<mask> of vectors that should be catched");
3168 register_command(cmd_ctx
, xscale_cmd
, "trace_buffer", xscale_handle_trace_buffer_command
, COMMAND_EXEC
, "<enable|disable> ['fill'|'wrap']");
3170 register_command(cmd_ctx
, xscale_cmd
, "dump_trace_buffer", xscale_handle_dump_trace_buffer_command
, COMMAND_EXEC
, "dump content of trace buffer");
3172 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)