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

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)