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

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)