1 /***************************************************************************
2 * Copyright (C) 2005 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 "arm7_9_common.h"
28 #include "embeddedice.h"
37 #define _DEBUG_INSTRUCTION_EXECUTION_
41 int arm9tdmi_register_commands(struct command_context_s
*cmd_ctx
);
43 /* forward declarations */
44 int arm9tdmi_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
);
45 int arm9tdmi_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
);
48 /* target function declarations */
49 enum target_state
arm9tdmi_poll(struct target_s
*target
);
50 int arm9tdmi_halt(target_t
*target
);
51 int arm9tdmi_read_memory(struct target_s
*target
, u32 address
, u32 size
, u32 count
, u8
*buffer
);
53 target_type_t arm9tdmi_target
=
58 .arch_state
= armv4_5_arch_state
,
61 .resume
= arm7_9_resume
,
64 .assert_reset
= arm7_9_assert_reset
,
65 .deassert_reset
= arm7_9_deassert_reset
,
66 .soft_reset_halt
= arm7_9_soft_reset_halt
,
68 .get_gdb_reg_list
= armv4_5_get_gdb_reg_list
,
70 .read_memory
= arm7_9_read_memory
,
71 .write_memory
= arm7_9_write_memory
,
72 .bulk_write_memory
= arm7_9_bulk_write_memory
,
74 .add_breakpoint
= arm7_9_add_breakpoint
,
75 .remove_breakpoint
= arm7_9_remove_breakpoint
,
76 .add_watchpoint
= arm7_9_add_watchpoint
,
77 .remove_watchpoint
= arm7_9_remove_watchpoint
,
79 .register_commands
= arm9tdmi_register_commands
,
80 .target_command
= arm9tdmi_target_command
,
81 .init_target
= arm9tdmi_init_target
,
85 int arm9tdmi_examine_debug_reason(target_t
*target
)
87 /* get pointers to arch-specific information */
88 armv4_5_common_t
*armv4_5
= target
->arch_info
;
89 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
91 /* only check the debug reason if we don't know it already */
92 if ((target
->debug_reason
!= DBG_REASON_DBGRQ
)
93 && (target
->debug_reason
!= DBG_REASON_SINGLESTEP
))
95 scan_field_t fields
[3];
100 jtag_add_end_state(TAP_PD
);
102 fields
[0].device
= arm7_9
->jtag_info
.chain_pos
;
103 fields
[0].num_bits
= 32;
104 fields
[0].out_value
= NULL
;
105 fields
[0].out_mask
= NULL
;
106 fields
[0].in_value
= databus
;
107 fields
[0].in_check_value
= NULL
;
108 fields
[0].in_check_mask
= NULL
;
109 fields
[0].in_handler
= NULL
;
110 fields
[0].in_handler_priv
= NULL
;
112 fields
[1].device
= arm7_9
->jtag_info
.chain_pos
;
113 fields
[1].num_bits
= 3;
114 fields
[1].out_value
= NULL
;
115 fields
[1].out_mask
= NULL
;
116 fields
[1].in_value
= &debug_reason
;
117 fields
[1].in_check_value
= NULL
;
118 fields
[1].in_check_mask
= NULL
;
119 fields
[1].in_handler
= NULL
;
120 fields
[1].in_handler_priv
= NULL
;
122 fields
[2].device
= arm7_9
->jtag_info
.chain_pos
;
123 fields
[2].num_bits
= 32;
124 fields
[2].out_value
= NULL
;
125 fields
[2].out_mask
= NULL
;
126 fields
[2].in_value
= instructionbus
;
127 fields
[2].in_check_value
= NULL
;
128 fields
[2].in_check_mask
= NULL
;
129 fields
[2].in_handler
= NULL
;
130 fields
[2].in_handler_priv
= NULL
;
132 arm_jtag_scann(&arm7_9
->jtag_info
, 0x1);
133 arm_jtag_set_instr(&arm7_9
->jtag_info
, arm7_9
->jtag_info
.intest_instr
);
135 jtag_add_dr_scan(3, fields
, TAP_PD
);
136 jtag_execute_queue();
138 fields
[0].in_value
= NULL
;
139 fields
[0].out_value
= databus
;
140 fields
[1].in_value
= NULL
;
141 fields
[1].out_value
= &debug_reason
;
142 fields
[2].in_value
= NULL
;
143 fields
[2].out_value
= instructionbus
;
145 jtag_add_dr_scan(3, fields
, TAP_PD
);
147 if (debug_reason
& 0x4)
148 if (debug_reason
& 0x2)
149 target
->debug_reason
= DBG_REASON_WPTANDBKPT
;
151 target
->debug_reason
= DBG_REASON_WATCHPOINT
;
153 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
159 /* put an instruction in the ARM9TDMI pipeline or write the data bus, and optionally read data */
160 int arm9tdmi_clock_out(arm_jtag_t
*jtag_info
, u32 instr
, u32 out
, u32
*in
, int sysspeed
)
162 scan_field_t fields
[3];
165 u8 sysspeed_buf
= 0x0;
168 buf_set_u32(out_buf
, 0, 32, out
);
170 instr
= flip_u32(instr
, 32);
171 buf_set_u32(instr_buf
, 0, 32, instr
);
174 buf_set_u32(&sysspeed_buf
, 2, 1, 1);
176 jtag_add_end_state(TAP_PD
);
177 arm_jtag_scann(jtag_info
, 0x1);
178 arm_jtag_set_instr(jtag_info
, jtag_info
->intest_instr
);
180 fields
[0].device
= jtag_info
->chain_pos
;
181 fields
[0].num_bits
= 32;
182 fields
[0].out_value
= out_buf
;
183 fields
[0].out_mask
= NULL
;
186 fields
[0].in_value
= (u8
*)in
;
189 fields
[0].in_value
= NULL
;
191 fields
[0].in_check_value
= NULL
;
192 fields
[0].in_check_mask
= NULL
;
193 fields
[0].in_handler
= NULL
;
194 fields
[0].in_handler_priv
= NULL
;
196 fields
[1].device
= jtag_info
->chain_pos
;
197 fields
[1].num_bits
= 3;
198 fields
[1].out_value
= &sysspeed_buf
;
199 fields
[1].out_mask
= NULL
;
200 fields
[1].in_value
= NULL
;
201 fields
[1].in_check_value
= NULL
;
202 fields
[1].in_check_mask
= NULL
;
203 fields
[1].in_handler
= NULL
;
204 fields
[1].in_handler_priv
= NULL
;
206 fields
[2].device
= jtag_info
->chain_pos
;
207 fields
[2].num_bits
= 32;
208 fields
[2].out_value
= instr_buf
;
209 fields
[2].out_mask
= NULL
;
210 fields
[2].in_value
= NULL
;
211 fields
[2].in_check_value
= NULL
;
212 fields
[2].in_check_mask
= NULL
;
213 fields
[2].in_handler
= NULL
;
214 fields
[2].in_handler_priv
= NULL
;
216 jtag_add_dr_scan(3, fields
, -1);
218 jtag_add_runtest(0, -1);
220 #ifdef _DEBUG_INSTRUCTION_EXECUTION_
223 jtag_execute_queue();
227 in_string
= buf_to_char((u8
*)in
, 32);
228 DEBUG("instr: 0x%8.8x, out: 0x%8.8x, in: %s", flip_u32(instr
, 32), out
, in_string
);
232 DEBUG("instr: 0x%8.8x, out: 0x%8.8x", flip_u32(instr
, 32), out
);
239 /* just read data (instruction and data-out = don't care) */
240 int arm9tdmi_clock_data_in(arm_jtag_t
*jtag_info
, u32
*in
)
242 scan_field_t fields
[3];
244 jtag_add_end_state(TAP_PD
);
245 arm_jtag_scann(jtag_info
, 0x1);
246 arm_jtag_set_instr(jtag_info
, jtag_info
->intest_instr
);
248 fields
[0].device
= jtag_info
->chain_pos
;
249 fields
[0].num_bits
= 32;
250 fields
[0].out_value
= NULL
;
251 fields
[0].out_mask
= NULL
;
252 fields
[0].in_value
= (u8
*)in
;
253 fields
[0].in_handler
= NULL
;
254 fields
[0].in_handler_priv
= NULL
;
255 fields
[0].in_check_value
= NULL
;
256 fields
[0].in_check_mask
= NULL
;
258 fields
[1].device
= jtag_info
->chain_pos
;
259 fields
[1].num_bits
= 3;
260 fields
[1].out_value
= NULL
;
261 fields
[1].out_mask
= NULL
;
262 fields
[1].in_value
= NULL
;
263 fields
[1].in_handler
= NULL
;
264 fields
[1].in_handler_priv
= NULL
;
265 fields
[1].in_check_value
= NULL
;
266 fields
[1].in_check_mask
= NULL
;
268 fields
[2].device
= jtag_info
->chain_pos
;
269 fields
[2].num_bits
= 32;
270 fields
[2].out_value
= NULL
;
271 fields
[2].out_mask
= NULL
;
272 fields
[2].in_value
= NULL
;
273 fields
[2].in_check_value
= NULL
;
274 fields
[2].in_check_mask
= NULL
;
275 fields
[2].in_handler
= NULL
;
276 fields
[2].in_handler_priv
= NULL
;
278 jtag_add_dr_scan(3, fields
, -1);
280 jtag_add_runtest(0, -1);
282 #ifdef _DEBUG_INSTRUCTION_EXECUTION_
285 jtag_execute_queue();
289 in_string
= buf_to_char((u8
*)in
, 32);
290 DEBUG("in: %s", in_string
);
299 void arm9tdmi_change_to_arm(target_t
*target
, u32
*r0
, u32
*pc
)
301 /* get pointers to arch-specific information */
302 armv4_5_common_t
*armv4_5
= target
->arch_info
;
303 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
304 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
306 /* save r0 before using it and put system in ARM state
307 * to allow common handling of ARM and THUMB debugging */
309 /* fetch STR r0, [r0] */
310 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_STR(0, 0), 0, NULL
, 0);
311 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
312 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
313 /* STR r0, [r0] in Memory */
314 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, r0
, 0);
316 /* MOV r0, r15 fetched, STR in Decode */
317 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_MOV(0, 15), 0, NULL
, 0);
318 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
319 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_STR(0, 0), 0, NULL
, 0);
320 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
321 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
322 /* nothing fetched, STR r0, [r0] in Memory */
323 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, pc
, 0);
326 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_MOV_IM(0, 0x0), 0, NULL
, 0);
327 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
328 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
331 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_BX(0), 0, NULL
, 0);
332 /* NOP fetched, BX in Decode, MOV in Execute */
333 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
334 /* NOP fetched, BX in Execute (1) */
335 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
337 jtag_execute_queue();
339 /* fix program counter:
340 * MOV r0, r15 was the 5th instruction (+8)
341 * reading PC in Thumb state gives address of instruction + 4
346 void arm9tdmi_read_core_regs(target_t
*target
, u32 mask
, u32
* core_regs
[16])
349 /* get pointers to arch-specific information */
350 armv4_5_common_t
*armv4_5
= target
->arch_info
;
351 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
352 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
354 /* STMIA r0-15, [r0] at debug speed
355 * register values will start to appear on 4th DCLK
357 arm9tdmi_clock_out(jtag_info
, ARMV4_5_STMIA(0, mask
& 0xffff, 0, 0), 0, NULL
, 0);
359 /* fetch NOP, STM in DECODE stage */
360 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
361 /* fetch NOP, STM in EXECUTE stage (1st cycle) */
362 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
364 for (i
= 0; i
<= 15; i
++)
367 /* nothing fetched, STM in MEMORY (i'th cycle) */
368 arm9tdmi_clock_data_in(jtag_info
, core_regs
[i
]);
373 void arm9tdmi_read_xpsr(target_t
*target
, u32
*xpsr
, int spsr
)
375 /* get pointers to arch-specific information */
376 armv4_5_common_t
*armv4_5
= target
->arch_info
;
377 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
378 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
381 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MRS(0, spsr
& 1), 0, NULL
, 0);
382 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
383 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
384 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
385 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
388 arm9tdmi_clock_out(jtag_info
, ARMV4_5_STR(0, 15), 0, NULL
, 0);
389 /* fetch NOP, STR in DECODE stage */
390 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
391 /* fetch NOP, STR in EXECUTE stage (1st cycle) */
392 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
393 /* nothing fetched, STR in MEMORY */
394 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, xpsr
, 0);
398 void arm9tdmi_write_xpsr(target_t
*target
, u32 xpsr
, int spsr
)
400 /* get pointers to arch-specific information */
401 armv4_5_common_t
*armv4_5
= target
->arch_info
;
402 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
403 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
405 DEBUG("xpsr: %8.8x, spsr: %i", xpsr
, spsr
);
408 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MSR_IM(xpsr
& 0xff, 0, 1, spsr
), 0, NULL
, 0);
409 /* MSR2 fetched, MSR1 in DECODE */
410 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MSR_IM((xpsr
& 0xff00) >> 8, 0xc, 2, spsr
), 0, NULL
, 0);
411 /* MSR3 fetched, MSR1 in EXECUTE (1), MSR2 in DECODE */
412 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MSR_IM((xpsr
& 0xff0000) >> 16, 0x8, 4, spsr
), 0, NULL
, 0);
413 /* nothing fetched, MSR1 in EXECUTE (2) */
414 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
415 /* nothing fetched, MSR1 in EXECUTE (3) */
416 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
417 /* MSR4 fetched, MSR2 in EXECUTE (1), MSR3 in DECODE */
418 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MSR_IM((xpsr
& 0xff000000) >> 24, 0x4, 8, spsr
), 0, NULL
, 0);
419 /* nothing fetched, MSR2 in EXECUTE (2) */
420 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
421 /* nothing fetched, MSR2 in EXECUTE (3) */
422 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
423 /* NOP fetched, MSR3 in EXECUTE (1), MSR4 in DECODE */
424 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
425 /* nothing fetched, MSR3 in EXECUTE (2) */
426 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
427 /* nothing fetched, MSR3 in EXECUTE (3) */
428 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
429 /* NOP fetched, MSR4 in EXECUTE (1) */
430 /* last MSR writes flags, which takes only one cycle */
431 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
434 void arm9tdmi_write_xpsr_im8(target_t
*target
, u8 xpsr_im
, int rot
, int spsr
)
436 /* get pointers to arch-specific information */
437 armv4_5_common_t
*armv4_5
= target
->arch_info
;
438 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
439 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
441 DEBUG("xpsr_im: %2.2x, rot: %i, spsr: %i", xpsr_im
, rot
, spsr
);
444 arm9tdmi_clock_out(jtag_info
, ARMV4_5_MSR_IM(xpsr_im
, rot
, 1, spsr
), 0, NULL
, 0);
445 /* NOP fetched, MSR in DECODE */
446 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
447 /* NOP fetched, MSR in EXECUTE (1) */
448 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
450 /* rot == 4 writes flags, which takes only one cycle */
453 /* nothing fetched, MSR in EXECUTE (2) */
454 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
455 /* nothing fetched, MSR in EXECUTE (3) */
456 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
460 void arm9tdmi_write_core_regs(target_t
*target
, u32 mask
, u32 core_regs
[16])
463 /* get pointers to arch-specific information */
464 armv4_5_common_t
*armv4_5
= target
->arch_info
;
465 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
466 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
468 /* LDMIA r0-15, [r0] at debug speed
469 * register values will start to appear on 4th DCLK
471 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDMIA(0, mask
& 0xffff, 0, 0), 0, NULL
, 0);
473 /* fetch NOP, LDM in DECODE stage */
474 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
475 /* fetch NOP, LDM in EXECUTE stage (1st cycle) */
476 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
478 for (i
= 0; i
<= 15; i
++)
481 /* nothing fetched, LDM still in EXECUTE (1+i cycle) */
482 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, core_regs
[i
], NULL
, 0);
484 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
488 void arm9tdmi_load_word_regs(target_t
*target
, u32 mask
)
490 /* get pointers to arch-specific information */
491 armv4_5_common_t
*armv4_5
= target
->arch_info
;
492 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
493 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
495 /* put system-speed load-multiple into the pipeline */
496 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDMIA(0, mask
& 0xffff, 0, 1), 0, NULL
, 0);
497 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
501 void arm9tdmi_load_hword_reg(target_t
*target
, int num
)
503 /* get pointers to arch-specific information */
504 armv4_5_common_t
*armv4_5
= target
->arch_info
;
505 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
506 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
508 /* put system-speed load half-word into the pipeline */
509 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDRH_IP(num
, 0), 0, NULL
, 0);
510 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
513 void arm9tdmi_load_byte_reg(target_t
*target
, int num
)
515 /* get pointers to arch-specific information */
516 armv4_5_common_t
*armv4_5
= target
->arch_info
;
517 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
518 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
520 /* put system-speed load byte into the pipeline */
521 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDRB_IP(num
, 0), 0, NULL
, 0);
522 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
526 void arm9tdmi_store_word_regs(target_t
*target
, u32 mask
)
528 /* get pointers to arch-specific information */
529 armv4_5_common_t
*armv4_5
= target
->arch_info
;
530 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
531 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
533 /* put system-speed store-multiple into the pipeline */
534 arm9tdmi_clock_out(jtag_info
, ARMV4_5_STMIA(0, mask
, 0, 1), 0, NULL
, 0);
535 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
539 void arm9tdmi_store_hword_reg(target_t
*target
, int num
)
541 /* get pointers to arch-specific information */
542 armv4_5_common_t
*armv4_5
= target
->arch_info
;
543 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
544 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
546 /* put system-speed store half-word into the pipeline */
547 arm9tdmi_clock_out(jtag_info
, ARMV4_5_STRH_IP(num
, 0), 0, NULL
, 0);
548 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
552 void arm9tdmi_store_byte_reg(target_t
*target
, int num
)
554 /* get pointers to arch-specific information */
555 armv4_5_common_t
*armv4_5
= target
->arch_info
;
556 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
557 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
559 /* put system-speed store byte into the pipeline */
560 arm9tdmi_clock_out(jtag_info
, ARMV4_5_STRB_IP(num
, 0), 0, NULL
, 0);
561 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
565 void arm9tdmi_write_pc(target_t
*target
, u32 pc
)
567 /* get pointers to arch-specific information */
568 armv4_5_common_t
*armv4_5
= target
->arch_info
;
569 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
570 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
572 /* LDMIA r0-15, [r0] at debug speed
573 * register values will start to appear on 4th DCLK
575 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDMIA(0, 0x8000, 0, 0), 0, NULL
, 0);
577 /* fetch NOP, LDM in DECODE stage */
578 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
579 /* fetch NOP, LDM in EXECUTE stage (1st cycle) */
580 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
581 /* nothing fetched, LDM in EXECUTE stage (2nd cycle) (output data) */
582 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, pc
, NULL
, 0);
583 /* nothing fetched, LDM in EXECUTE stage (3rd cycle) */
584 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
585 /* fetch NOP, LDM in EXECUTE stage (4th cycle) */
586 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
587 /* fetch NOP, LDM in EXECUTE stage (5th cycle) */
588 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
592 void arm9tdmi_branch_resume(target_t
*target
)
594 /* get pointers to arch-specific information */
595 armv4_5_common_t
*armv4_5
= target
->arch_info
;
596 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
597 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
599 arm9tdmi_clock_out(jtag_info
, ARMV4_5_B(0xfffffc, 0), 0, NULL
, 0);
600 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 1);
604 void arm9tdmi_branch_resume_thumb(target_t
*target
)
608 /* get pointers to arch-specific information */
609 armv4_5_common_t
*armv4_5
= target
->arch_info
;
610 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
611 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
612 reg_t
*dbg_stat
= &arm7_9
->eice_cache
->reg_list
[EICE_DBG_STAT
];
614 /* LDMIA r0-15, [r0] at debug speed
615 * register values will start to appear on 4th DCLK
617 arm9tdmi_clock_out(jtag_info
, ARMV4_5_LDMIA(0, 0x1, 0, 0), 0, NULL
, 0);
619 /* fetch NOP, LDM in DECODE stage */
620 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
621 /* fetch NOP, LDM in EXECUTE stage (1st cycle) */
622 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
623 /* nothing fetched, LDM in EXECUTE stage (2nd cycle) */
624 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, buf_get_u32(armv4_5
->core_cache
->reg_list
[15].value
, 0, 32) | 1, NULL
, 0);
625 /* nothing fetched, LDM in EXECUTE stage (3rd cycle) */
626 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
628 /* Branch and eXchange */
629 arm9tdmi_clock_out(jtag_info
, ARMV4_5_BX(0), 0, NULL
, 0);
631 embeddedice_read_reg(dbg_stat
);
633 /* fetch NOP, BX in DECODE stage */
634 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
636 embeddedice_read_reg(dbg_stat
);
638 /* fetch NOP, BX in EXECUTE stage (1st cycle) */
639 arm9tdmi_clock_out(jtag_info
, ARMV4_5_NOP
, 0, NULL
, 0);
641 /* target is now in Thumb state */
642 embeddedice_read_reg(dbg_stat
);
644 /* clean r0 bits to avoid alignment problems */
645 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_MOV_IM(0, 0x0), 0, NULL
, 0);
646 /* load r0 value, MOV_IM in Decode*/
647 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_LDR(0, 0), 0, NULL
, 0);
648 /* fetch NOP, LDR in Decode, MOV_IM in Execute */
649 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
650 /* fetch NOP, LDR in Execute */
651 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
652 /* nothing fetched, LDR in EXECUTE stage (2nd cycle) */
653 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, buf_get_u32(armv4_5
->core_cache
->reg_list
[0].value
, 0, 32), NULL
, 0);
654 /* nothing fetched, LDR in EXECUTE stage (3rd cycle) */
655 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
657 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
658 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
660 embeddedice_read_reg(dbg_stat
);
662 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_B(0x7f6), 0, NULL
, 1);
663 arm9tdmi_clock_out(jtag_info
, ARMV4_5_T_NOP
, 0, NULL
, 0);
667 void arm9tdmi_enable_single_step(target_t
*target
)
669 /* get pointers to arch-specific information */
670 armv4_5_common_t
*armv4_5
= target
->arch_info
;
671 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
672 arm9tdmi_common_t
*arm9
= arm7_9
->arch_info
;
674 if (arm9
->has_single_step
)
676 buf_set_u32(arm7_9
->eice_cache
->reg_list
[EICE_DBG_CTRL
].value
, 3, 1, 1);
677 embeddedice_store_reg(&arm7_9
->eice_cache
->reg_list
[EICE_DBG_CTRL
]);
681 arm7_9_enable_eice_step(target
);
685 void arm9tdmi_disable_single_step(target_t
*target
)
687 /* get pointers to arch-specific information */
688 armv4_5_common_t
*armv4_5
= target
->arch_info
;
689 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
690 arm9tdmi_common_t
*arm9
= arm7_9
->arch_info
;
692 if (arm9
->has_single_step
)
694 buf_set_u32(arm7_9
->eice_cache
->reg_list
[EICE_DBG_CTRL
].value
, 3, 1, 0);
695 embeddedice_store_reg(&arm7_9
->eice_cache
->reg_list
[EICE_DBG_CTRL
]);
699 arm7_9_disable_eice_step(target
);
703 void arm9tdmi_build_reg_cache(target_t
*target
)
705 reg_cache_t
**cache_p
= register_get_last_cache_p(&target
->reg_cache
);
706 /* get pointers to arch-specific information */
707 armv4_5_common_t
*armv4_5
= target
->arch_info
;
708 arm7_9_common_t
*arm7_9
= armv4_5
->arch_info
;
709 arm_jtag_t
*jtag_info
= &arm7_9
->jtag_info
;
710 arm9tdmi_common_t
*arm9tdmi
= arm7_9
->arch_info
;
713 (*cache_p
) = armv4_5_build_reg_cache(target
, armv4_5
);
714 armv4_5
->core_cache
= (*cache_p
);
716 (*cache_p
)->next
= embeddedice_build_reg_cache(target
, jtag_info
, 0);
717 arm7_9
->eice_cache
= (*cache_p
)->next
;
719 if (arm9tdmi
->has_monitor_mode
)
720 (*cache_p
)->next
->reg_list
[0].size
= 6;
722 (*cache_p
)->next
->reg_list
[0].size
= 4;
724 (*cache_p
)->next
->reg_list
[1].size
= 5;
728 int arm9tdmi_init_target(struct command_context_s
*cmd_ctx
, struct target_s
*target
)
731 arm9tdmi_build_reg_cache(target
);
743 int arm9tdmi_init_arch_info(target_t
*target
, arm9tdmi_common_t
*arm9tdmi
, int chain_pos
, char *variant
)
745 armv4_5_common_t
*armv4_5
;
746 arm7_9_common_t
*arm7_9
;
748 arm7_9
= &arm9tdmi
->arm7_9_common
;
749 armv4_5
= &arm7_9
->armv4_5_common
;
751 /* prepare JTAG information for the new target */
752 arm7_9
->jtag_info
.chain_pos
= chain_pos
;
753 arm7_9
->jtag_info
.scann_size
= 5;
755 /* register arch-specific functions */
756 arm7_9
->examine_debug_reason
= arm9tdmi_examine_debug_reason
;
757 arm7_9
->change_to_arm
= arm9tdmi_change_to_arm
;
758 arm7_9
->read_core_regs
= arm9tdmi_read_core_regs
;
759 arm7_9
->read_xpsr
= arm9tdmi_read_xpsr
;
761 arm7_9
->write_xpsr
= arm9tdmi_write_xpsr
;
762 arm7_9
->write_xpsr_im8
= arm9tdmi_write_xpsr_im8
;
763 arm7_9
->write_core_regs
= arm9tdmi_write_core_regs
;
765 arm7_9
->load_word_regs
= arm9tdmi_load_word_regs
;
766 arm7_9
->load_hword_reg
= arm9tdmi_load_hword_reg
;
767 arm7_9
->load_byte_reg
= arm9tdmi_load_byte_reg
;
769 arm7_9
->store_word_regs
= arm9tdmi_store_word_regs
;
770 arm7_9
->store_hword_reg
= arm9tdmi_store_hword_reg
;
771 arm7_9
->store_byte_reg
= arm9tdmi_store_byte_reg
;
773 arm7_9
->write_pc
= arm9tdmi_write_pc
;
774 arm7_9
->branch_resume
= arm9tdmi_branch_resume
;
775 arm7_9
->branch_resume_thumb
= arm9tdmi_branch_resume_thumb
;
777 arm7_9
->enable_single_step
= arm9tdmi_enable_single_step
;
778 arm7_9
->disable_single_step
= arm9tdmi_disable_single_step
;
780 arm7_9
->pre_debug_entry
= NULL
;
781 arm7_9
->post_debug_entry
= NULL
;
783 arm7_9
->pre_restore_context
= NULL
;
784 arm7_9
->post_restore_context
= NULL
;
786 /* initialize arch-specific breakpoint handling */
787 buf_set_u32((u8
*)(&arm7_9
->arm_bkpt
), 0, 32, 0xdeeedeee);
788 buf_set_u32((u8
*)(&arm7_9
->thumb_bkpt
), 0, 16, 0xdeee);
790 arm7_9
->sw_bkpts_use_wp
= 1;
791 arm7_9
->sw_bkpts_enabled
= 0;
792 arm7_9
->dbgreq_adjust_pc
= 3;
793 arm7_9
->arch_info
= arm9tdmi
;
794 arm7_9
->use_dbgrq
= 1;
796 arm9tdmi
->common_magic
= ARM9TDMI_COMMON_MAGIC
;
797 arm9tdmi
->has_monitor_mode
= 0;
798 arm9tdmi
->has_single_step
= 0;
799 arm9tdmi
->arch_info
= NULL
;
803 if (strcmp(variant
, "arm920t") == 0)
804 arm9tdmi
->has_single_step
= 1;
805 else if (strcmp(variant
, "arm922t") == 0)
806 arm9tdmi
->has_single_step
= 1;
807 else if (strcmp(variant
, "arm940t") == 0)
808 arm9tdmi
->has_single_step
= 1;
811 arm7_9_init_arch_info(target
, arm7_9
);
816 /* target arm9tdmi <endianess> <startup_mode> <chain_pos> <variant>*/
817 int arm9tdmi_target_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct target_s
*target
)
820 char *variant
= NULL
;
821 arm9tdmi_common_t
*arm9tdmi
= malloc(sizeof(arm9tdmi_common_t
));
825 ERROR("'target arm9tdmi' requires at least one additional argument");
829 chain_pos
= strtoul(args
[3], NULL
, 0);
832 variant
= strdup(args
[4]);
834 arm9tdmi_init_arch_info(target
, arm9tdmi
, chain_pos
, variant
);
839 int arm9tdmi_register_commands(struct command_context_s
*cmd_ctx
)
843 retval
= arm7_9_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)