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

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)