b62bc49399b5d3bf51ac54fb4bd2d6d517a824e0
[openocd.git] / src / target / arm926ejs.c
1 /***************************************************************************
2 * Copyright (C) 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
4 * *
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. *
9 * *
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. *
14 * *
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 ***************************************************************************/
20 #ifdef HAVE_CONFIG_H
21 #include "config.h"
22 #endif
23
24 #include "arm926ejs.h"
25 #include "jtag.h"
26 #include "log.h"
27
28 #include <stdlib.h>
29 #include <string.h>
30
31 #if 1
32 #define _DEBUG_INSTRUCTION_EXECUTION_
33 #endif
34
35 /* cli handling */
36 int arm926ejs_register_commands(struct command_context_s *cmd_ctx);
37
38 int arm926ejs_handle_cp15_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
39 int arm926ejs_handle_cp15i_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
40 int arm926ejs_handle_virt2phys_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
41 int arm926ejs_handle_cache_info_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
42 int arm926ejs_handle_md_phys_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
43 int arm926ejs_handle_mw_phys_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
44
45 int arm926ejs_handle_read_cache_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
46 int arm926ejs_handle_read_mmu_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
47
48 /* forward declarations */
49 int arm926ejs_target_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct target_s *target);
50 int arm926ejs_init_target(struct command_context_s *cmd_ctx, struct target_s *target);
51 int arm926ejs_quit();
52 int arm926ejs_arch_state(struct target_s *target, char *buf, int buf_size);
53 int arm926ejs_read_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer);
54 int arm926ejs_write_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer);
55 int arm926ejs_soft_reset_halt(struct target_s *target);
56
57 #define ARM926EJS_CP15_ADDR(opcode_1, opcode_2, CRn, CRm) ((opcode_1 << 11) | (opcode_2 << 8) | (CRn << 4) | (CRm << 0))
58
59 target_type_t arm926ejs_target =
60 {
61 .name = "arm926ejs",
62
63 .poll = arm7_9_poll,
64 .arch_state = arm926ejs_arch_state,
65
66 .halt = arm7_9_halt,
67 .resume = arm7_9_resume,
68 .step = arm7_9_step,
69
70 .assert_reset = arm7_9_assert_reset,
71 .deassert_reset = arm7_9_deassert_reset,
72 .soft_reset_halt = arm926ejs_soft_reset_halt,
73 .prepare_reset_halt = arm7_9_prepare_reset_halt,
74
75 .get_gdb_reg_list = armv4_5_get_gdb_reg_list,
76
77 .read_memory = arm7_9_read_memory,
78 .write_memory = arm926ejs_write_memory,
79 .bulk_write_memory = arm7_9_bulk_write_memory,
80
81 .run_algorithm = armv4_5_run_algorithm,
82
83 .add_breakpoint = arm7_9_add_breakpoint,
84 .remove_breakpoint = arm7_9_remove_breakpoint,
85 .add_watchpoint = arm7_9_add_watchpoint,
86 .remove_watchpoint = arm7_9_remove_watchpoint,
87
88 .register_commands = arm926ejs_register_commands,
89 .target_command = arm926ejs_target_command,
90 .init_target = arm926ejs_init_target,
91 .quit = arm926ejs_quit
92 };
93
94 int arm926ejs_catch_broken_irscan(u8 *in_value, void *priv)
95 {
96 /* The ARM926EJ-S' instruction register is 4 bits wide */
97 *in_value &= 0xf;
98
99 if ((*in_value == 0x0f) || (*in_value == 0x00))
100 {
101 DEBUG("caught ARM926EJ-S invalid Capture-IR result after CP15 access");
102 return ERROR_OK;
103 }
104 else
105 {
106 return ERROR_JTAG_QUEUE_FAILED;
107 }
108 }
109
110 int arm926ejs_read_cp15(target_t *target, u32 address, u32 *value)
111 {
112 armv4_5_common_t *armv4_5 = target->arch_info;
113 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
114 arm_jtag_t *jtag_info = &arm7_9->jtag_info;
115 scan_field_t fields[4];
116 u8 address_buf[2];
117 u8 nr_w_buf = 0;
118 u8 access = 1;
119 error_handler_t error_handler;
120
121 buf_set_u32(address_buf, 0, 14, address);
122
123 jtag_add_end_state(TAP_RTI);
124 arm_jtag_scann(jtag_info, 0xf);
125 arm_jtag_set_instr(jtag_info, jtag_info->intest_instr, NULL);
126
127 fields[0].device = jtag_info->chain_pos;
128 fields[0].num_bits = 32;
129 fields[0].out_value = NULL;
130 fields[0].out_mask = NULL;
131 fields[0].in_value = NULL;
132 fields[0].in_check_value = NULL;
133 fields[0].in_check_mask = NULL;
134 fields[0].in_handler = NULL;
135 fields[0].in_handler_priv = NULL;
136
137 fields[1].device = jtag_info->chain_pos;
138 fields[1].num_bits = 1;
139 fields[1].out_value = &access;
140 fields[1].out_mask = NULL;
141 fields[1].in_value = &access;
142 fields[1].in_check_value = NULL;
143 fields[1].in_check_mask = NULL;
144 fields[1].in_handler = NULL;
145 fields[1].in_handler_priv = NULL;
146
147 fields[2].device = jtag_info->chain_pos;
148 fields[2].num_bits = 14;
149 fields[2].out_value = address_buf;
150 fields[2].out_mask = NULL;
151 fields[2].in_value = NULL;
152 fields[2].in_check_value = NULL;
153 fields[2].in_check_mask = NULL;
154 fields[2].in_handler = NULL;
155 fields[2].in_handler_priv = NULL;
156
157 fields[3].device = jtag_info->chain_pos;
158 fields[3].num_bits = 1;
159 fields[3].out_value = &nr_w_buf;
160 fields[3].out_mask = NULL;
161 fields[3].in_value = NULL;
162 fields[3].in_check_value = NULL;
163 fields[3].in_check_mask = NULL;
164 fields[3].in_handler = NULL;
165 fields[3].in_handler_priv = NULL;
166
167 jtag_add_dr_scan(4, fields, -1, NULL);
168
169 fields[0].in_handler_priv = value;
170 fields[0].in_handler = arm_jtag_buf_to_u32;
171
172 do
173 {
174 /* rescan with NOP, to wait for the access to complete */
175 access = 0;
176 nr_w_buf = 0;
177 jtag_add_dr_scan(4, fields, -1, NULL);
178 jtag_execute_queue();
179 } while (buf_get_u32(&access, 0, 1) != 1);
180
181 #ifdef _DEBUG_INSTRUCTION_EXECUTION_
182 DEBUG("addr: 0x%x value: %8.8x", address, *value);
183 #endif
184
185 error_handler.error_handler = arm926ejs_catch_broken_irscan;
186 error_handler.error_handler_priv = NULL;
187
188 arm_jtag_set_instr(jtag_info, 0xc, &error_handler);
189
190 return ERROR_OK;
191 }
192
193 int arm926ejs_write_cp15(target_t *target, u32 address, u32 value)
194 {
195 armv4_5_common_t *armv4_5 = target->arch_info;
196 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
197 arm_jtag_t *jtag_info = &arm7_9->jtag_info;
198 scan_field_t fields[4];
199 u8 value_buf[4];
200 u8 address_buf[2];
201 u8 nr_w_buf = 1;
202 u8 access = 1;
203 error_handler_t error_handler;
204
205 buf_set_u32(address_buf, 0, 14, address);
206 buf_set_u32(value_buf, 0, 32, value);
207
208 jtag_add_end_state(TAP_RTI);
209 arm_jtag_scann(jtag_info, 0xf);
210 arm_jtag_set_instr(jtag_info, jtag_info->intest_instr, NULL);
211
212 fields[0].device = jtag_info->chain_pos;
213 fields[0].num_bits = 32;
214 fields[0].out_value = value_buf;
215 fields[0].out_mask = NULL;
216 fields[0].in_value = NULL;
217 fields[0].in_check_value = NULL;
218 fields[0].in_check_mask = NULL;
219 fields[0].in_handler = NULL;
220 fields[0].in_handler_priv = NULL;
221
222 fields[1].device = jtag_info->chain_pos;
223 fields[1].num_bits = 1;
224 fields[1].out_value = &access;
225 fields[1].out_mask = NULL;
226 fields[1].in_value = &access;
227 fields[1].in_check_value = NULL;
228 fields[1].in_check_mask = NULL;
229 fields[1].in_handler = NULL;
230 fields[1].in_handler_priv = NULL;
231
232 fields[2].device = jtag_info->chain_pos;
233 fields[2].num_bits = 14;
234 fields[2].out_value = address_buf;
235 fields[2].out_mask = NULL;
236 fields[2].in_value = NULL;
237 fields[2].in_check_value = NULL;
238 fields[2].in_check_mask = NULL;
239 fields[2].in_handler = NULL;
240 fields[2].in_handler_priv = NULL;
241
242 fields[3].device = jtag_info->chain_pos;
243 fields[3].num_bits = 1;
244 fields[3].out_value = &nr_w_buf;
245 fields[3].out_mask = NULL;
246 fields[3].in_value = NULL;
247 fields[3].in_check_value = NULL;
248 fields[3].in_check_mask = NULL;
249 fields[3].in_handler = NULL;
250 fields[3].in_handler_priv = NULL;
251
252 jtag_add_dr_scan(4, fields, -1, NULL);
253
254 do
255 {
256 /* rescan with NOP, to wait for the access to complete */
257 access = 0;
258 nr_w_buf = 0;
259 jtag_add_dr_scan(4, fields, -1, NULL);
260 jtag_execute_queue();
261 } while (buf_get_u32(&access, 0, 1) != 1);
262
263 #ifdef _DEBUG_INSTRUCTION_EXECUTION_
264 DEBUG("addr: 0x%x value: %8.8x", address, value);
265 #endif
266
267 error_handler.error_handler = arm926ejs_catch_broken_irscan;
268 error_handler.error_handler_priv = NULL;
269
270 arm_jtag_set_instr(jtag_info, 0xf, &error_handler);
271
272 return ERROR_OK;
273 }
274
275 int arm926ejs_examine_debug_reason(target_t *target)
276 {
277 armv4_5_common_t *armv4_5 = target->arch_info;
278 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
279 reg_t *dbg_stat = &arm7_9->eice_cache->reg_list[EICE_DBG_STAT];
280 int debug_reason;
281 int retval;
282
283 embeddedice_read_reg(dbg_stat);
284 if ((retval = jtag_execute_queue()) != ERROR_OK)
285 return retval;
286
287 debug_reason = buf_get_u32(dbg_stat->value, 6, 4);
288
289 switch (debug_reason)
290 {
291 case 1:
292 DEBUG("breakpoint from EICE unit 0");
293 target->debug_reason = DBG_REASON_BREAKPOINT;
294 break;
295 case 2:
296 DEBUG("breakpoint from EICE unit 1");
297 target->debug_reason = DBG_REASON_BREAKPOINT;
298 break;
299 case 3:
300 DEBUG("soft breakpoint (BKPT instruction)");
301 target->debug_reason = DBG_REASON_BREAKPOINT;
302 break;
303 case 4:
304 DEBUG("vector catch breakpoint");
305 target->debug_reason = DBG_REASON_BREAKPOINT;
306 break;
307 case 5:
308 DEBUG("external breakpoint");
309 target->debug_reason = DBG_REASON_BREAKPOINT;
310 break;
311 case 6:
312 DEBUG("watchpoint from EICE unit 0");
313 target->debug_reason = DBG_REASON_WATCHPOINT;
314 break;
315 case 7:
316 DEBUG("watchpoint from EICE unit 1");
317 target->debug_reason = DBG_REASON_WATCHPOINT;
318 break;
319 case 8:
320 DEBUG("external watchpoint");
321 target->debug_reason = DBG_REASON_WATCHPOINT;
322 break;
323 case 9:
324 DEBUG("internal debug request");
325 target->debug_reason = DBG_REASON_DBGRQ;
326 break;
327 case 10:
328 DEBUG("external debug request");
329 target->debug_reason = DBG_REASON_DBGRQ;
330 break;
331 case 11:
332 ERROR("BUG: debug re-entry from system speed access shouldn't be handled here");
333 break;
334 default:
335 ERROR("BUG: unknown debug reason: 0x%x", debug_reason);
336 target->debug_reason = DBG_REASON_DBGRQ;
337 }
338
339 return ERROR_OK;
340 }
341
342 u32 arm926ejs_get_ttb(target_t *target)
343 {
344 int retval;
345 u32 ttb = 0x0;
346
347 if ((retval = arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 2, 0), &ttb)) != ERROR_OK)
348 return retval;
349
350 return ttb;
351 }
352
353 void arm926ejs_disable_mmu_caches(target_t *target, int mmu, int d_u_cache, int i_cache)
354 {
355 u32 cp15_control;
356
357 /* read cp15 control register */
358 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 1, 0), &cp15_control);
359 jtag_execute_queue();
360
361 if (mmu)
362 {
363 /* invalidate TLB */
364 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 8, 7), 0x0);
365
366 cp15_control &= ~0x1U;
367 }
368
369 if (d_u_cache)
370 {
371 u32 debug_override;
372 /* read-modify-write CP15 debug override register
373 * to enable "test and clean all" */
374 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 15, 0), &debug_override);
375 debug_override |= 0x80000;
376 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 15, 0), debug_override);
377
378 /* clean and invalidate DCache */
379 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 7, 5), 0x0);
380
381 /* write CP15 debug override register
382 * to disable "test and clean all" */
383 debug_override &= ~0x80000;
384 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 15, 0), debug_override);
385
386 cp15_control &= ~0x4U;
387 }
388
389 if (i_cache)
390 {
391 /* invalidate ICache */
392 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 7, 5), 0x0);
393
394 cp15_control &= ~0x1000U;
395 }
396
397 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 1, 0), cp15_control);
398 }
399
400 void arm926ejs_enable_mmu_caches(target_t *target, int mmu, int d_u_cache, int i_cache)
401 {
402 u32 cp15_control;
403
404 /* read cp15 control register */
405 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 1, 0), &cp15_control);
406 jtag_execute_queue();
407
408 if (mmu)
409 cp15_control |= 0x1U;
410
411 if (d_u_cache)
412 cp15_control |= 0x4U;
413
414 if (i_cache)
415 cp15_control |= 0x1000U;
416
417 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 1, 0), cp15_control);
418 }
419
420 void arm926ejs_post_debug_entry(target_t *target)
421 {
422 armv4_5_common_t *armv4_5 = target->arch_info;
423 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
424 arm9tdmi_common_t *arm9tdmi = arm7_9->arch_info;
425 arm926ejs_common_t *arm926ejs = arm9tdmi->arch_info;
426
427 /* examine cp15 control reg */
428 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 1, 0), &arm926ejs->cp15_control_reg);
429 jtag_execute_queue();
430 DEBUG("cp15_control_reg: %8.8x", arm926ejs->cp15_control_reg);
431
432 if (arm926ejs->armv4_5_mmu.armv4_5_cache.ctype == -1)
433 {
434 u32 cache_type_reg;
435 /* identify caches */
436 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 1, 0, 0), &cache_type_reg);
437 jtag_execute_queue();
438 armv4_5_identify_cache(cache_type_reg, &arm926ejs->armv4_5_mmu.armv4_5_cache);
439 }
440
441 arm926ejs->armv4_5_mmu.mmu_enabled = (arm926ejs->cp15_control_reg & 0x1U) ? 1 : 0;
442 arm926ejs->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled = (arm926ejs->cp15_control_reg & 0x4U) ? 1 : 0;
443 arm926ejs->armv4_5_mmu.armv4_5_cache.i_cache_enabled = (arm926ejs->cp15_control_reg & 0x1000U) ? 1 : 0;
444
445 /* save i/d fault status and address register */
446 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 5, 0), &arm926ejs->d_fsr);
447 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 1, 5, 0), &arm926ejs->i_fsr);
448 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 6, 0), &arm926ejs->d_far);
449
450 DEBUG("D FSR: 0x%8.8x, D FAR: 0x%8.8x, I FSR: 0x%8.8x",
451 arm926ejs->d_fsr, arm926ejs->d_far, arm926ejs->i_fsr);
452
453
454 u32 cache_dbg_ctrl;
455
456 /* read-modify-write CP15 cache debug control register
457 * to disable I/D-cache linefills and force WT */
458 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(7, 0, 15, 0), &cache_dbg_ctrl);
459 cache_dbg_ctrl |= 0x7;
460 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(7, 0, 15, 0), cache_dbg_ctrl);
461 }
462
463 void arm926ejs_pre_restore_context(target_t *target)
464 {
465 armv4_5_common_t *armv4_5 = target->arch_info;
466 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
467 arm9tdmi_common_t *arm9tdmi = arm7_9->arch_info;
468 arm926ejs_common_t *arm926ejs = arm9tdmi->arch_info;
469
470 /* restore i/d fault status and address register */
471 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 5, 0), arm926ejs->d_fsr);
472 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 1, 5, 0), arm926ejs->i_fsr);
473 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 6, 0), arm926ejs->d_far);
474
475 u32 cache_dbg_ctrl;
476
477 /* read-modify-write CP15 cache debug control register
478 * to reenable I/D-cache linefills and disable WT */
479 arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(7, 0, 15, 0), &cache_dbg_ctrl);
480 cache_dbg_ctrl &= ~0x7;
481 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(7, 0, 15, 0), cache_dbg_ctrl);
482 }
483
484 int arm926ejs_get_arch_pointers(target_t *target, armv4_5_common_t **armv4_5_p, arm7_9_common_t **arm7_9_p, arm9tdmi_common_t **arm9tdmi_p, arm926ejs_common_t **arm926ejs_p)
485 {
486 armv4_5_common_t *armv4_5 = target->arch_info;
487 arm7_9_common_t *arm7_9;
488 arm9tdmi_common_t *arm9tdmi;
489 arm926ejs_common_t *arm926ejs;
490
491 if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC)
492 {
493 return -1;
494 }
495
496 arm7_9 = armv4_5->arch_info;
497 if (arm7_9->common_magic != ARM7_9_COMMON_MAGIC)
498 {
499 return -1;
500 }
501
502 arm9tdmi = arm7_9->arch_info;
503 if (arm9tdmi->common_magic != ARM9TDMI_COMMON_MAGIC)
504 {
505 return -1;
506 }
507
508 arm926ejs = arm9tdmi->arch_info;
509 if (arm926ejs->common_magic != ARM926EJS_COMMON_MAGIC)
510 {
511 return -1;
512 }
513
514 *armv4_5_p = armv4_5;
515 *arm7_9_p = arm7_9;
516 *arm9tdmi_p = arm9tdmi;
517 *arm926ejs_p = arm926ejs;
518
519 return ERROR_OK;
520 }
521
522 int arm926ejs_arch_state(struct target_s *target, char *buf, int buf_size)
523 {
524 armv4_5_common_t *armv4_5 = target->arch_info;
525 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
526 arm9tdmi_common_t *arm9tdmi = arm7_9->arch_info;
527 arm926ejs_common_t *arm926ejs = arm9tdmi->arch_info;
528
529 char *state[] =
530 {
531 "disabled", "enabled"
532 };
533
534 if (armv4_5->common_magic != ARMV4_5_COMMON_MAGIC)
535 {
536 ERROR("BUG: called for a non-ARMv4/5 target");
537 exit(-1);
538 }
539
540 snprintf(buf, buf_size,
541 "target halted in %s state due to %s, current mode: %s\n"
542 "cpsr: 0x%8.8x pc: 0x%8.8x\n"
543 "MMU: %s, D-Cache: %s, I-Cache: %s",
544 armv4_5_state_strings[armv4_5->core_state],
545 target_debug_reason_strings[target->debug_reason],
546 armv4_5_mode_strings[armv4_5_mode_to_number(armv4_5->core_mode)],
547 buf_get_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 32),
548 buf_get_u32(armv4_5->core_cache->reg_list[15].value, 0, 32),
549 state[arm926ejs->armv4_5_mmu.mmu_enabled],
550 state[arm926ejs->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled],
551 state[arm926ejs->armv4_5_mmu.armv4_5_cache.i_cache_enabled]);
552
553 return ERROR_OK;
554 }
555
556 int arm926ejs_soft_reset_halt(struct target_s *target)
557 {
558 armv4_5_common_t *armv4_5 = target->arch_info;
559 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
560 arm9tdmi_common_t *arm9tdmi = arm7_9->arch_info;
561 arm926ejs_common_t *arm926ejs = arm9tdmi->arch_info;
562 reg_t *dbg_stat = &arm7_9->eice_cache->reg_list[EICE_DBG_STAT];
563
564 if (target->state == TARGET_RUNNING)
565 {
566 target->type->halt(target);
567 }
568
569 while (buf_get_u32(dbg_stat->value, EICE_DBG_STATUS_DBGACK, 1) == 0)
570 {
571 embeddedice_read_reg(dbg_stat);
572 jtag_execute_queue();
573 }
574
575 target->state = TARGET_HALTED;
576
577 /* SVC, ARM state, IRQ and FIQ disabled */
578 buf_set_u32(armv4_5->core_cache->reg_list[ARMV4_5_CPSR].value, 0, 8, 0xd3);
579 armv4_5->core_cache->reg_list[ARMV4_5_CPSR].dirty = 1;
580 armv4_5->core_cache->reg_list[ARMV4_5_CPSR].valid = 1;
581
582 /* start fetching from 0x0 */
583 buf_set_u32(armv4_5->core_cache->reg_list[15].value, 0, 32, 0x0);
584 armv4_5->core_cache->reg_list[15].dirty = 1;
585 armv4_5->core_cache->reg_list[15].valid = 1;
586
587 armv4_5->core_mode = ARMV4_5_MODE_SVC;
588 armv4_5->core_state = ARMV4_5_STATE_ARM;
589
590 arm926ejs_disable_mmu_caches(target, 1, 1, 1);
591 arm926ejs->armv4_5_mmu.mmu_enabled = 0;
592 arm926ejs->armv4_5_mmu.armv4_5_cache.d_u_cache_enabled = 0;
593 arm926ejs->armv4_5_mmu.armv4_5_cache.i_cache_enabled = 0;
594
595 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
596
597 return ERROR_OK;
598 }
599
600 int arm926ejs_write_memory(struct target_s *target, u32 address, u32 size, u32 count, u8 *buffer)
601 {
602 int retval;
603 armv4_5_common_t *armv4_5 = target->arch_info;
604 arm7_9_common_t *arm7_9 = armv4_5->arch_info;
605 arm9tdmi_common_t *arm9tdmi = arm7_9->arch_info;
606 arm926ejs_common_t *arm926ejs = arm9tdmi->arch_info;
607
608 if ((retval = arm7_9_write_memory(target, address, size, count, buffer)) != ERROR_OK)
609 return retval;
610
611 /* If ICache is enabled, we have to invalidate affected ICache lines
612 * the DCache is forced to write-through, so we don't have to clean it here
613 */
614 if (arm926ejs->armv4_5_mmu.armv4_5_cache.i_cache_enabled)
615 {
616 if (count <= 1)
617 {
618 /* invalidate ICache single entry with MVA */
619 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 1, 7, 5), address);
620 }
621 else
622 {
623 /* invalidate ICache */
624 arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(0, 0, 7, 5), address);
625 }
626 }
627
628 return retval;
629 }
630
631 int arm926ejs_init_target(struct command_context_s *cmd_ctx, struct target_s *target)
632 {
633 arm9tdmi_init_target(cmd_ctx, target);
634
635 return ERROR_OK;
636
637 }
638
639 int arm926ejs_quit()
640 {
641
642 return ERROR_OK;
643 }
644
645 int arm926ejs_init_arch_info(target_t *target, arm926ejs_common_t *arm926ejs, int chain_pos, char *variant)
646 {
647 arm9tdmi_common_t *arm9tdmi = &arm926ejs->arm9tdmi_common;
648 arm7_9_common_t *arm7_9 = &arm9tdmi->arm7_9_common;
649
650 /* initialize arm9tdmi specific info (including arm7_9 and armv4_5)
651 */
652 arm9tdmi_init_arch_info(target, arm9tdmi, chain_pos, variant);
653
654 arm9tdmi->arch_info = arm926ejs;
655 arm926ejs->common_magic = ARM926EJS_COMMON_MAGIC;
656
657 arm7_9->post_debug_entry = arm926ejs_post_debug_entry;
658 arm7_9->pre_restore_context = arm926ejs_pre_restore_context;
659
660 arm926ejs->armv4_5_mmu.armv4_5_cache.ctype = -1;
661 arm926ejs->armv4_5_mmu.get_ttb = arm926ejs_get_ttb;
662 arm926ejs->armv4_5_mmu.read_memory = arm7_9_read_memory;
663 arm926ejs->armv4_5_mmu.write_memory = arm7_9_write_memory;
664 arm926ejs->armv4_5_mmu.disable_mmu_caches = arm926ejs_disable_mmu_caches;
665 arm926ejs->armv4_5_mmu.enable_mmu_caches = arm926ejs_enable_mmu_caches;
666 arm926ejs->armv4_5_mmu.has_tiny_pages = 1;
667 arm926ejs->armv4_5_mmu.mmu_enabled = 0;
668
669 arm7_9->examine_debug_reason = arm926ejs_examine_debug_reason;
670
671 /* The ARM926EJ-S implements the ARMv5TE architecture which
672 * has the BKPT instruction, so we don't have to use a watchpoint comparator
673 */
674 arm7_9->arm_bkpt = ARMV5_BKPT(0x0);
675 arm7_9->thumb_bkpt = ARMV5_T_BKPT(0x0) & 0xffff;
676
677 arm7_9->sw_bkpts_use_wp = 0;
678 arm7_9->sw_bkpts_enabled = 1;
679
680 return ERROR_OK;
681 }
682
683 int arm926ejs_target_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct target_s *target)
684 {
685 int chain_pos;
686 char *variant = NULL;
687 arm926ejs_common_t *arm926ejs = malloc(sizeof(arm926ejs_common_t));
688
689 if (argc < 4)
690 {
691 ERROR("'target arm926ejs' requires at least one additional argument");
692 exit(-1);
693 }
694
695 chain_pos = strtoul(args[3], NULL, 0);
696
697 if (argc >= 5)
698 variant = args[4];
699
700 DEBUG("chain_pos: %i, variant: %s", chain_pos, variant);
701
702 arm926ejs_init_arch_info(target, arm926ejs, chain_pos, variant);
703
704 return ERROR_OK;
705 }
706
707 int arm926ejs_register_commands(struct command_context_s *cmd_ctx)
708 {
709 int retval;
710 command_t *arm926ejs_cmd;
711
712
713 retval = arm9tdmi_register_commands(cmd_ctx);
714
715 arm926ejs_cmd = register_command(cmd_ctx, NULL, "arm926ejs", NULL, COMMAND_ANY, "arm926ejs specific commands");
716
717 register_command(cmd_ctx, arm926ejs_cmd, "cp15", arm926ejs_handle_cp15_command, COMMAND_EXEC, "display/modify cp15 register <opcode_1> <opcode_2> <CRn> <CRm> [value]");
718
719 register_command(cmd_ctx, arm926ejs_cmd, "cache_info", arm926ejs_handle_cache_info_command, COMMAND_EXEC, "display information about target caches");
720 register_command(cmd_ctx, arm926ejs_cmd, "virt2phys", arm926ejs_handle_virt2phys_command, COMMAND_EXEC, "translate va to pa <va>");
721
722 register_command(cmd_ctx, arm926ejs_cmd, "mdw_phys", arm926ejs_handle_md_phys_command, COMMAND_EXEC, "display memory words <physical addr> [count]");
723 register_command(cmd_ctx, arm926ejs_cmd, "mdh_phys", arm926ejs_handle_md_phys_command, COMMAND_EXEC, "display memory half-words <physical addr> [count]");
724 register_command(cmd_ctx, arm926ejs_cmd, "mdb_phys", arm926ejs_handle_md_phys_command, COMMAND_EXEC, "display memory bytes <physical addr> [count]");
725
726 register_command(cmd_ctx, arm926ejs_cmd, "mww_phys", arm926ejs_handle_mw_phys_command, COMMAND_EXEC, "write memory word <physical addr> <value>");
727 register_command(cmd_ctx, arm926ejs_cmd, "mwh_phys", arm926ejs_handle_mw_phys_command, COMMAND_EXEC, "write memory half-word <physical addr> <value>");
728 register_command(cmd_ctx, arm926ejs_cmd, "mwb_phys", arm926ejs_handle_mw_phys_command, COMMAND_EXEC, "write memory byte <physical addr> <value>");
729
730 return ERROR_OK;
731 }
732
733 int arm926ejs_handle_cp15_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
734 {
735 int retval;
736 target_t *target = get_current_target(cmd_ctx);
737 armv4_5_common_t *armv4_5;
738 arm7_9_common_t *arm7_9;
739 arm9tdmi_common_t *arm9tdmi;
740 arm926ejs_common_t *arm926ejs;
741 int opcode_1;
742 int opcode_2;
743 int CRn;
744 int CRm;
745
746 if ((argc < 4) || (argc > 5))
747 {
748 command_print(cmd_ctx, "usage: arm926ejs cp15 <opcode_1> <opcode_2> <CRn> <CRm> [value]");
749 return ERROR_OK;
750 }
751
752 opcode_1 = strtoul(args[0], NULL, 0);
753 opcode_2 = strtoul(args[1], NULL, 0);
754 CRn = strtoul(args[2], NULL, 0);
755 CRm = strtoul(args[3], NULL, 0);
756
757 if (arm926ejs_get_arch_pointers(target, &armv4_5, &arm7_9, &arm9tdmi, &arm926ejs) != ERROR_OK)
758 {
759 command_print(cmd_ctx, "current target isn't an ARM926EJ-S target");
760 return ERROR_OK;
761 }
762
763 if (target->state != TARGET_HALTED)
764 {
765 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
766 return ERROR_OK;
767 }
768
769 if (argc == 4)
770 {
771 u32 value;
772 if ((retval = arm926ejs_read_cp15(target, ARM926EJS_CP15_ADDR(opcode_1, opcode_2, CRn, CRm), &value)) != ERROR_OK)
773 {
774 command_print(cmd_ctx, "couldn't access register");
775 return ERROR_OK;
776 }
777 jtag_execute_queue();
778
779 command_print(cmd_ctx, "%i %i %i %i: %8.8x", opcode_1, opcode_2, CRn, CRm, value);
780 }
781 else
782 {
783 u32 value = strtoul(args[4], NULL, 0);
784 if ((retval = arm926ejs_write_cp15(target, ARM926EJS_CP15_ADDR(opcode_1, opcode_2, CRn, CRm), value)) != ERROR_OK)
785 {
786 command_print(cmd_ctx, "couldn't access register");
787 return ERROR_OK;
788 }
789 command_print(cmd_ctx, "%i %i %i %i: %8.8x", opcode_1, opcode_2, CRn, CRm, value);
790 }
791
792 return ERROR_OK;
793 }
794
795 int arm926ejs_handle_cache_info_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
796 {
797 target_t *target = get_current_target(cmd_ctx);
798 armv4_5_common_t *armv4_5;
799 arm7_9_common_t *arm7_9;
800 arm9tdmi_common_t *arm9tdmi;
801 arm926ejs_common_t *arm926ejs;
802
803 if (arm926ejs_get_arch_pointers(target, &armv4_5, &arm7_9, &arm9tdmi, &arm926ejs) != ERROR_OK)
804 {
805 command_print(cmd_ctx, "current target isn't an ARM926EJ-S target");
806 return ERROR_OK;
807 }
808
809 return armv4_5_handle_cache_info_command(cmd_ctx, &arm926ejs->armv4_5_mmu.armv4_5_cache);
810 }
811
812 int arm926ejs_handle_virt2phys_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
813 {
814 target_t *target = get_current_target(cmd_ctx);
815 armv4_5_common_t *armv4_5;
816 arm7_9_common_t *arm7_9;
817 arm9tdmi_common_t *arm9tdmi;
818 arm926ejs_common_t *arm926ejs;
819 arm_jtag_t *jtag_info;
820
821 if (arm926ejs_get_arch_pointers(target, &armv4_5, &arm7_9, &arm9tdmi, &arm926ejs) != ERROR_OK)
822 {
823 command_print(cmd_ctx, "current target isn't an ARM926EJ-S target");
824 return ERROR_OK;
825 }
826
827 jtag_info = &arm7_9->jtag_info;
828
829 if (target->state != TARGET_HALTED)
830 {
831 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
832 return ERROR_OK;
833 }
834
835 return armv4_5_mmu_handle_virt2phys_command(cmd_ctx, cmd, args, argc, target, &arm926ejs->armv4_5_mmu);
836 }
837
838 int arm926ejs_handle_md_phys_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
839 {
840 target_t *target = get_current_target(cmd_ctx);
841 armv4_5_common_t *armv4_5;
842 arm7_9_common_t *arm7_9;
843 arm9tdmi_common_t *arm9tdmi;
844 arm926ejs_common_t *arm926ejs;
845 arm_jtag_t *jtag_info;
846
847 if (arm926ejs_get_arch_pointers(target, &armv4_5, &arm7_9, &arm9tdmi, &arm926ejs) != ERROR_OK)
848 {
849 command_print(cmd_ctx, "current target isn't an ARM926EJ-S target");
850 return ERROR_OK;
851 }
852
853 jtag_info = &arm7_9->jtag_info;
854
855 if (target->state != TARGET_HALTED)
856 {
857 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
858 return ERROR_OK;
859 }
860
861 return armv4_5_mmu_handle_md_phys_command(cmd_ctx, cmd, args, argc, target, &arm926ejs->armv4_5_mmu);
862 }
863
864 int arm926ejs_handle_mw_phys_command(command_context_t *cmd_ctx, char *cmd, char **args, int argc)
865 {
866 target_t *target = get_current_target(cmd_ctx);
867 armv4_5_common_t *armv4_5;
868 arm7_9_common_t *arm7_9;
869 arm9tdmi_common_t *arm9tdmi;
870 arm926ejs_common_t *arm926ejs;
871 arm_jtag_t *jtag_info;
872
873 if (arm926ejs_get_arch_pointers(target, &armv4_5, &arm7_9, &arm9tdmi, &arm926ejs) != ERROR_OK)
874 {
875 command_print(cmd_ctx, "current target isn't an ARM926EJ-S target");
876 return ERROR_OK;
877 }
878
879 jtag_info = &arm7_9->jtag_info;
880
881 if (target->state != TARGET_HALTED)
882 {
883 command_print(cmd_ctx, "target must be stopped for \"%s\" command", cmd);
884 return ERROR_OK;
885 }
886
887 return armv4_5_mmu_handle_mw_phys_command(cmd_ctx, cmd, args, argc, target, &arm926ejs->armv4_5_mmu);
888 }

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)