cortex_m: target implementation renames cortex_m3 to cortex_m
[openocd.git] / src / target / hla_target.c
1 /***************************************************************************
2 * Copyright (C) 2011 by Mathias Kuester *
3 * Mathias Kuester <kesmtp@freenet.de> *
4 * *
5 * Copyright (C) 2011 by Spencer Oliver *
6 * spen@spen-soft.co.uk *
7 * *
8 * revised: 4/25/13 by brent@mbari.org [DCC target request support] *
9 * *
10 * This program is free software; you can redistribute it and/or modify *
11 * it under the terms of the GNU General Public License as published by *
12 * the Free Software Foundation; either version 2 of the License, or *
13 * (at your option) any later version. *
14 * *
15 * This program is distributed in the hope that it will be useful, *
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
18 * GNU General Public License for more details. *
19 * *
20 * You should have received a copy of the GNU General Public License *
21 * along with this program; if not, write to the *
22 * Free Software Foundation, Inc., *
23 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. *
24 ***************************************************************************/
25
26 #ifdef HAVE_CONFIG_H
27 #include "config.h"
28 #endif
29
30 #include "jtag/jtag.h"
31 #include "jtag/hla/hla_transport.h"
32 #include "jtag/hla/hla_interface.h"
33 #include "jtag/hla/hla_layout.h"
34 #include "register.h"
35 #include "algorithm.h"
36 #include "target.h"
37 #include "breakpoints.h"
38 #include "target_type.h"
39 #include "armv7m.h"
40 #include "cortex_m.h"
41 #include "arm_semihosting.h"
42 #include "target_request.h"
43
44 #define savedDCRDR dbgbase /* FIXME: using target->dbgbase to preserve DCRDR */
45
46 #define ARMV7M_SCS_DCRSR DCB_DCRSR
47 #define ARMV7M_SCS_DCRDR DCB_DCRDR
48
49 static inline struct hl_interface_s *target_to_adapter(struct target *target)
50 {
51 return target->tap->priv;
52 }
53
54 static int adapter_load_core_reg_u32(struct target *target,
55 uint32_t num, uint32_t *value)
56 {
57 int retval;
58 struct hl_interface_s *adapter = target_to_adapter(target);
59
60 LOG_DEBUG("%s", __func__);
61
62 /* NOTE: we "know" here that the register identifiers used
63 * in the v7m header match the Cortex-M3 Debug Core Register
64 * Selector values for R0..R15, xPSR, MSP, and PSP.
65 */
66 switch (num) {
67 case 0 ... 18:
68 /* read a normal core register */
69 retval = adapter->layout->api->read_reg(adapter->fd, num, value);
70
71 if (retval != ERROR_OK) {
72 LOG_ERROR("JTAG failure %i", retval);
73 return ERROR_JTAG_DEVICE_ERROR;
74 }
75 LOG_DEBUG("load from core reg %i value 0x%" PRIx32 "", (int)num, *value);
76 break;
77
78 case ARMV7M_FPSID:
79 case ARMV7M_FPEXC:
80 *value = 0;
81 break;
82
83 case ARMV7M_FPSCR:
84 /* Floating-point Status and Registers */
85 retval = target_write_u32(target, ARMV7M_SCS_DCRSR, 33);
86 if (retval != ERROR_OK)
87 return retval;
88 retval = target_read_u32(target, ARMV7M_SCS_DCRDR, value);
89 if (retval != ERROR_OK)
90 return retval;
91 LOG_DEBUG("load from core reg %i value 0x%" PRIx32 "", (int)num, *value);
92 break;
93
94 case ARMV7M_S0 ... ARMV7M_S31:
95 /* Floating-point Status and Registers */
96 retval = target_write_u32(target, ARMV7M_SCS_DCRSR, num-ARMV7M_S0+64);
97 if (retval != ERROR_OK)
98 return retval;
99 retval = target_read_u32(target, ARMV7M_SCS_DCRDR, value);
100 if (retval != ERROR_OK)
101 return retval;
102 LOG_DEBUG("load from core reg %i value 0x%" PRIx32 "", (int)num, *value);
103 break;
104
105 case ARMV7M_D0 ... ARMV7M_D15:
106 value = 0;
107 break;
108
109 case ARMV7M_PRIMASK:
110 case ARMV7M_BASEPRI:
111 case ARMV7M_FAULTMASK:
112 case ARMV7M_CONTROL:
113 /* Cortex-M3 packages these four registers as bitfields
114 * in one Debug Core register. So say r0 and r2 docs;
115 * it was removed from r1 docs, but still works.
116 */
117 retval = adapter->layout->api->read_reg(adapter->fd, 20, value);
118 if (retval != ERROR_OK)
119 return retval;
120
121 switch (num) {
122 case ARMV7M_PRIMASK:
123 *value = buf_get_u32((uint8_t *) value, 0, 1);
124 break;
125
126 case ARMV7M_BASEPRI:
127 *value = buf_get_u32((uint8_t *) value, 8, 8);
128 break;
129
130 case ARMV7M_FAULTMASK:
131 *value = buf_get_u32((uint8_t *) value, 16, 1);
132 break;
133
134 case ARMV7M_CONTROL:
135 *value = buf_get_u32((uint8_t *) value, 24, 2);
136 break;
137 }
138
139 LOG_DEBUG("load from special reg %i value 0x%" PRIx32 "",
140 (int)num, *value);
141 break;
142
143 default:
144 return ERROR_COMMAND_SYNTAX_ERROR;
145 }
146
147 return ERROR_OK;
148 }
149
150 static int adapter_store_core_reg_u32(struct target *target,
151 uint32_t num, uint32_t value)
152 {
153 int retval;
154 uint32_t reg;
155 struct armv7m_common *armv7m = target_to_armv7m(target);
156 struct hl_interface_s *adapter = target_to_adapter(target);
157
158 LOG_DEBUG("%s", __func__);
159
160 /* NOTE: we "know" here that the register identifiers used
161 * in the v7m header match the Cortex-M3 Debug Core Register
162 * Selector values for R0..R15, xPSR, MSP, and PSP.
163 */
164 switch (num) {
165 case 0 ... 18:
166 retval = adapter->layout->api->write_reg(adapter->fd, num, value);
167
168 if (retval != ERROR_OK) {
169 struct reg *r;
170
171 LOG_ERROR("JTAG failure");
172 r = armv7m->arm.core_cache->reg_list + num;
173 r->dirty = r->valid;
174 return ERROR_JTAG_DEVICE_ERROR;
175 }
176 LOG_DEBUG("write core reg %i value 0x%" PRIx32 "", (int)num, value);
177 break;
178
179 case ARMV7M_FPSID:
180 case ARMV7M_FPEXC:
181 break;
182
183 case ARMV7M_FPSCR:
184 /* Floating-point Status and Registers */
185 retval = target_write_u32(target, ARMV7M_SCS_DCRDR, value);
186 if (retval != ERROR_OK)
187 return retval;
188 retval = target_write_u32(target, ARMV7M_SCS_DCRSR, 33 | (1<<16));
189 if (retval != ERROR_OK)
190 return retval;
191 LOG_DEBUG("write core reg %i value 0x%" PRIx32 "", (int)num, value);
192 break;
193
194 case ARMV7M_S0 ... ARMV7M_S31:
195 /* Floating-point Status and Registers */
196 retval = target_write_u32(target, ARMV7M_SCS_DCRDR, value);
197 if (retval != ERROR_OK)
198 return retval;
199 retval = target_write_u32(target, ARMV7M_SCS_DCRSR, (num-ARMV7M_S0+64) | (1<<16));
200 if (retval != ERROR_OK)
201 return retval;
202 LOG_DEBUG("write core reg %i value 0x%" PRIx32 "", (int)num, value);
203 break;
204
205 case ARMV7M_D0 ... ARMV7M_D15:
206 break;
207
208 case ARMV7M_PRIMASK:
209 case ARMV7M_BASEPRI:
210 case ARMV7M_FAULTMASK:
211 case ARMV7M_CONTROL:
212 /* Cortex-M3 packages these four registers as bitfields
213 * in one Debug Core register. So say r0 and r2 docs;
214 * it was removed from r1 docs, but still works.
215 */
216
217 adapter->layout->api->read_reg(adapter->fd, 20, &reg);
218
219 switch (num) {
220 case ARMV7M_PRIMASK:
221 buf_set_u32((uint8_t *) &reg, 0, 1, value);
222 break;
223
224 case ARMV7M_BASEPRI:
225 buf_set_u32((uint8_t *) &reg, 8, 8, value);
226 break;
227
228 case ARMV7M_FAULTMASK:
229 buf_set_u32((uint8_t *) &reg, 16, 1, value);
230 break;
231
232 case ARMV7M_CONTROL:
233 buf_set_u32((uint8_t *) &reg, 24, 2, value);
234 break;
235 }
236
237 adapter->layout->api->write_reg(adapter->fd, 20, reg);
238
239 LOG_DEBUG("write special reg %i value 0x%" PRIx32 " ", (int)num, value);
240 break;
241
242 default:
243 return ERROR_COMMAND_SYNTAX_ERROR;
244 }
245
246 return ERROR_OK;
247 }
248
249 static int adapter_examine_debug_reason(struct target *target)
250 {
251 if ((target->debug_reason != DBG_REASON_DBGRQ)
252 && (target->debug_reason != DBG_REASON_SINGLESTEP)) {
253 target->debug_reason = DBG_REASON_BREAKPOINT;
254 }
255
256 return ERROR_OK;
257 }
258
259 static int hl_dcc_read(struct hl_interface_s *hl_if, uint8_t *value, uint8_t *ctrl)
260 {
261 uint16_t dcrdr;
262 int retval = hl_if->layout->api->read_mem(hl_if->fd,
263 DCB_DCRDR, 1, sizeof(dcrdr), (uint8_t *)&dcrdr);
264 if (retval == ERROR_OK) {
265 *ctrl = (uint8_t)dcrdr;
266 *value = (uint8_t)(dcrdr >> 8);
267
268 LOG_DEBUG("data 0x%x ctrl 0x%x", *value, *ctrl);
269
270 if (dcrdr & 1) {
271 /* write ack back to software dcc register
272 * to signify we have read data */
273 /* atomically clear just the byte containing the busy bit */
274 static const uint8_t zero;
275 retval = hl_if->layout->api->write_mem(hl_if->fd, DCB_DCRDR, 1, 1, &zero);
276 }
277 }
278 return retval;
279 }
280
281 static int hl_target_request_data(struct target *target,
282 uint32_t size, uint8_t *buffer)
283 {
284 struct hl_interface_s *hl_if = target_to_adapter(target);
285 uint8_t data;
286 uint8_t ctrl;
287 uint32_t i;
288
289 for (i = 0; i < (size * 4); i++) {
290 hl_dcc_read(hl_if, &data, &ctrl);
291 buffer[i] = data;
292 }
293
294 return ERROR_OK;
295 }
296
297 static int hl_handle_target_request(void *priv)
298 {
299 struct target *target = priv;
300 if (!target_was_examined(target))
301 return ERROR_OK;
302 struct hl_interface_s *hl_if = target_to_adapter(target);
303
304 if (!target->dbg_msg_enabled)
305 return ERROR_OK;
306
307 if (target->state == TARGET_RUNNING) {
308 uint8_t data;
309 uint8_t ctrl;
310
311 hl_dcc_read(hl_if, &data, &ctrl);
312
313 /* check if we have data */
314 if (ctrl & (1 << 0)) {
315 uint32_t request;
316
317 /* we assume target is quick enough */
318 request = data;
319 hl_dcc_read(hl_if, &data, &ctrl);
320 request |= (data << 8);
321 hl_dcc_read(hl_if, &data, &ctrl);
322 request |= (data << 16);
323 hl_dcc_read(hl_if, &data, &ctrl);
324 request |= (data << 24);
325 target_request(target, request);
326 }
327 }
328
329 return ERROR_OK;
330 }
331
332 static int adapter_init_arch_info(struct target *target,
333 struct cortex_m_common *cortex_m,
334 struct jtag_tap *tap)
335 {
336 struct armv7m_common *armv7m;
337
338 LOG_DEBUG("%s", __func__);
339
340 armv7m = &cortex_m->armv7m;
341 armv7m_init_arch_info(target, armv7m);
342
343 armv7m->load_core_reg_u32 = adapter_load_core_reg_u32;
344 armv7m->store_core_reg_u32 = adapter_store_core_reg_u32;
345
346 armv7m->examine_debug_reason = adapter_examine_debug_reason;
347 armv7m->stlink = true;
348
349 target_register_timer_callback(hl_handle_target_request, 1, 1, target);
350
351 return ERROR_OK;
352 }
353
354 static int adapter_init_target(struct command_context *cmd_ctx,
355 struct target *target)
356 {
357 LOG_DEBUG("%s", __func__);
358
359 armv7m_build_reg_cache(target);
360
361 return ERROR_OK;
362 }
363
364 static int adapter_target_create(struct target *target,
365 Jim_Interp *interp)
366 {
367 LOG_DEBUG("%s", __func__);
368
369 struct cortex_m_common *cortex_m = calloc(1, sizeof(struct cortex_m_common));
370
371 if (!cortex_m)
372 return ERROR_COMMAND_SYNTAX_ERROR;
373
374 adapter_init_arch_info(target, cortex_m, target->tap);
375
376 return ERROR_OK;
377 }
378
379 static int adapter_load_context(struct target *target)
380 {
381 struct armv7m_common *armv7m = target_to_armv7m(target);
382 int num_regs = armv7m->arm.core_cache->num_regs;
383
384 for (int i = 0; i < num_regs; i++) {
385
386 struct reg *r = &armv7m->arm.core_cache->reg_list[i];
387 if (!r->valid)
388 armv7m->arm.read_core_reg(target, r, i, ARM_MODE_ANY);
389 }
390
391 return ERROR_OK;
392 }
393
394 static int adapter_debug_entry(struct target *target)
395 {
396 struct hl_interface_s *adapter = target_to_adapter(target);
397 struct armv7m_common *armv7m = target_to_armv7m(target);
398 struct arm *arm = &armv7m->arm;
399 struct reg *r;
400 uint32_t xPSR;
401 int retval;
402
403 /* preserve the DCRDR across halts */
404 retval = target_read_u32(target, DCB_DCRDR, &target->savedDCRDR);
405 if (retval != ERROR_OK)
406 return retval;
407
408 retval = armv7m->examine_debug_reason(target);
409 if (retval != ERROR_OK)
410 return retval;
411
412 adapter_load_context(target);
413
414 /* make sure we clear the vector catch bit */
415 adapter->layout->api->write_debug_reg(adapter->fd, DCB_DEMCR, TRCENA);
416
417 r = arm->cpsr;
418 xPSR = buf_get_u32(r->value, 0, 32);
419
420 /* Are we in an exception handler */
421 if (xPSR & 0x1FF) {
422 armv7m->exception_number = (xPSR & 0x1FF);
423
424 arm->core_mode = ARM_MODE_HANDLER;
425 arm->map = armv7m_msp_reg_map;
426 } else {
427 unsigned control = buf_get_u32(arm->core_cache
428 ->reg_list[ARMV7M_CONTROL].value, 0, 2);
429
430 /* is this thread privileged? */
431 arm->core_mode = control & 1
432 ? ARM_MODE_USER_THREAD
433 : ARM_MODE_THREAD;
434
435 /* which stack is it using? */
436 if (control & 2)
437 arm->map = armv7m_psp_reg_map;
438 else
439 arm->map = armv7m_msp_reg_map;
440
441 armv7m->exception_number = 0;
442 }
443
444 LOG_DEBUG("entered debug state in core mode: %s at PC 0x%08" PRIx32 ", target->state: %s",
445 arm_mode_name(arm->core_mode),
446 *(uint32_t *)(arm->pc->value),
447 target_state_name(target));
448
449 return retval;
450 }
451
452 static int adapter_poll(struct target *target)
453 {
454 enum target_state state;
455 struct hl_interface_s *adapter = target_to_adapter(target);
456 struct armv7m_common *armv7m = target_to_armv7m(target);
457 enum target_state prev_target_state = target->state;
458
459 state = adapter->layout->api->state(adapter->fd);
460
461 if (state == TARGET_UNKNOWN) {
462 LOG_ERROR("jtag status contains invalid mode value - communication failure");
463 return ERROR_TARGET_FAILURE;
464 }
465
466 if (target->state == state)
467 return ERROR_OK;
468
469 if (state == TARGET_HALTED) {
470 target->state = state;
471
472 int retval = adapter_debug_entry(target);
473 if (retval != ERROR_OK)
474 return retval;
475
476 if (prev_target_state == TARGET_DEBUG_RUNNING) {
477 target_call_event_callbacks(target, TARGET_EVENT_DEBUG_HALTED);
478 } else {
479 if (arm_semihosting(target, &retval) != 0)
480 return retval;
481
482 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
483 }
484
485 LOG_DEBUG("halted: PC: 0x%08x", buf_get_u32(armv7m->arm.pc->value, 0, 32));
486 }
487
488 return ERROR_OK;
489 }
490
491 static int adapter_assert_reset(struct target *target)
492 {
493 int res = ERROR_OK;
494 struct hl_interface_s *adapter = target_to_adapter(target);
495 struct armv7m_common *armv7m = target_to_armv7m(target);
496 bool use_srst_fallback = true;
497
498 LOG_DEBUG("%s", __func__);
499
500 enum reset_types jtag_reset_config = jtag_get_reset_config();
501
502 bool srst_asserted = false;
503
504 if ((jtag_reset_config & RESET_HAS_SRST) &&
505 (jtag_reset_config & RESET_SRST_NO_GATING)) {
506 jtag_add_reset(0, 1);
507 res = adapter->layout->api->assert_srst(adapter->fd, 0);
508 srst_asserted = true;
509 }
510
511 adapter->layout->api->write_debug_reg(adapter->fd, DCB_DHCSR, DBGKEY|C_DEBUGEN);
512
513 /* only set vector catch if halt is requested */
514 if (target->reset_halt)
515 adapter->layout->api->write_debug_reg(adapter->fd, DCB_DEMCR, TRCENA|VC_CORERESET);
516 else
517 adapter->layout->api->write_debug_reg(adapter->fd, DCB_DEMCR, TRCENA);
518
519 if (jtag_reset_config & RESET_HAS_SRST) {
520 if (!srst_asserted) {
521 jtag_add_reset(0, 1);
522 res = adapter->layout->api->assert_srst(adapter->fd, 0);
523 }
524 if (res == ERROR_COMMAND_NOTFOUND)
525 LOG_ERROR("Hardware srst not supported, falling back to software reset");
526 else if (res == ERROR_OK) {
527 /* hardware srst supported */
528 use_srst_fallback = false;
529 }
530 }
531
532 if (use_srst_fallback) {
533 /* stlink v1 api does not support hardware srst, so we use a software reset fallback */
534 adapter->layout->api->write_debug_reg(adapter->fd, NVIC_AIRCR, AIRCR_VECTKEY | AIRCR_SYSRESETREQ);
535 }
536
537 res = adapter->layout->api->reset(adapter->fd);
538
539 if (res != ERROR_OK)
540 return res;
541
542 /* registers are now invalid */
543 register_cache_invalidate(armv7m->arm.core_cache);
544
545 if (target->reset_halt) {
546 target->state = TARGET_RESET;
547 target->debug_reason = DBG_REASON_DBGRQ;
548 } else {
549 target->state = TARGET_HALTED;
550 }
551
552 return ERROR_OK;
553 }
554
555 static int adapter_deassert_reset(struct target *target)
556 {
557 struct hl_interface_s *adapter = target_to_adapter(target);
558
559 enum reset_types jtag_reset_config = jtag_get_reset_config();
560
561 LOG_DEBUG("%s", __func__);
562
563 if (jtag_reset_config & RESET_HAS_SRST)
564 adapter->layout->api->assert_srst(adapter->fd, 1);
565
566 /* virtual deassert reset, we need it for the internal
567 * jtag state machine
568 */
569 jtag_add_reset(0, 0);
570
571 target->savedDCRDR = 0; /* clear both DCC busy bits on initial resume */
572
573 return target->reset_halt ? ERROR_OK : target_resume(target, 1, 0, 0, 0);
574 }
575
576 static int adapter_halt(struct target *target)
577 {
578 int res;
579 struct hl_interface_s *adapter = target_to_adapter(target);
580
581 LOG_DEBUG("%s", __func__);
582
583 if (target->state == TARGET_HALTED) {
584 LOG_DEBUG("target was already halted");
585 return ERROR_OK;
586 }
587
588 if (target->state == TARGET_UNKNOWN)
589 LOG_WARNING("target was in unknown state when halt was requested");
590
591 res = adapter->layout->api->halt(adapter->fd);
592
593 if (res != ERROR_OK)
594 return res;
595
596 target->debug_reason = DBG_REASON_DBGRQ;
597
598 return ERROR_OK;
599 }
600
601 static int adapter_resume(struct target *target, int current,
602 uint32_t address, int handle_breakpoints,
603 int debug_execution)
604 {
605 int res;
606 struct hl_interface_s *adapter = target_to_adapter(target);
607 struct armv7m_common *armv7m = target_to_armv7m(target);
608 uint32_t resume_pc;
609 struct breakpoint *breakpoint = NULL;
610 struct reg *pc;
611
612 LOG_DEBUG("%s %d 0x%08x %d %d", __func__, current, address,
613 handle_breakpoints, debug_execution);
614
615 if (target->state != TARGET_HALTED) {
616 LOG_WARNING("target not halted");
617 return ERROR_TARGET_NOT_HALTED;
618 }
619
620 if (!debug_execution) {
621 target_free_all_working_areas(target);
622 cortex_m_enable_breakpoints(target);
623 cortex_m_enable_watchpoints(target);
624 }
625
626 pc = armv7m->arm.pc;
627 if (!current) {
628 buf_set_u32(pc->value, 0, 32, address);
629 pc->dirty = true;
630 pc->valid = true;
631 }
632
633 if (!breakpoint_find(target, buf_get_u32(pc->value, 0, 32))
634 && !debug_execution) {
635 armv7m_maybe_skip_bkpt_inst(target, NULL);
636 }
637
638 resume_pc = buf_get_u32(pc->value, 0, 32);
639
640 /* write any user vector flags */
641 res = target_write_u32(target, DCB_DEMCR, TRCENA | armv7m->demcr);
642 if (res != ERROR_OK)
643 return res;
644
645 armv7m_restore_context(target);
646
647 /* restore savedDCRDR */
648 res = target_write_u32(target, DCB_DCRDR, target->savedDCRDR);
649 if (res != ERROR_OK)
650 return res;
651
652 /* registers are now invalid */
653 register_cache_invalidate(armv7m->arm.core_cache);
654
655 /* the front-end may request us not to handle breakpoints */
656 if (handle_breakpoints) {
657 /* Single step past breakpoint at current address */
658 breakpoint = breakpoint_find(target, resume_pc);
659 if (breakpoint) {
660 LOG_DEBUG("unset breakpoint at 0x%8.8" PRIx32 " (ID: %d)",
661 breakpoint->address,
662 breakpoint->unique_id);
663 cortex_m_unset_breakpoint(target, breakpoint);
664
665 res = adapter->layout->api->step(adapter->fd);
666
667 if (res != ERROR_OK)
668 return res;
669
670 cortex_m_set_breakpoint(target, breakpoint);
671 }
672 }
673
674 res = adapter->layout->api->run(adapter->fd);
675
676 if (res != ERROR_OK)
677 return res;
678
679 target->debug_reason = DBG_REASON_NOTHALTED;
680
681 if (!debug_execution) {
682 target->state = TARGET_RUNNING;
683 target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
684 } else {
685 target->state = TARGET_DEBUG_RUNNING;
686 target_call_event_callbacks(target, TARGET_EVENT_DEBUG_RESUMED);
687 }
688
689 return ERROR_OK;
690 }
691
692 static int adapter_step(struct target *target, int current,
693 uint32_t address, int handle_breakpoints)
694 {
695 int res;
696 struct hl_interface_s *adapter = target_to_adapter(target);
697 struct armv7m_common *armv7m = target_to_armv7m(target);
698 struct breakpoint *breakpoint = NULL;
699 struct reg *pc = armv7m->arm.pc;
700 bool bkpt_inst_found = false;
701
702 LOG_DEBUG("%s", __func__);
703
704 if (target->state != TARGET_HALTED) {
705 LOG_WARNING("target not halted");
706 return ERROR_TARGET_NOT_HALTED;
707 }
708
709 if (!current) {
710 buf_set_u32(pc->value, 0, 32, address);
711 pc->dirty = true;
712 pc->valid = true;
713 }
714
715 uint32_t pc_value = buf_get_u32(pc->value, 0, 32);
716
717 /* the front-end may request us not to handle breakpoints */
718 if (handle_breakpoints) {
719 breakpoint = breakpoint_find(target, pc_value);
720 if (breakpoint)
721 cortex_m_unset_breakpoint(target, breakpoint);
722 }
723
724 armv7m_maybe_skip_bkpt_inst(target, &bkpt_inst_found);
725
726 target->debug_reason = DBG_REASON_SINGLESTEP;
727
728 armv7m_restore_context(target);
729
730 /* restore savedDCRDR */
731 res = target_write_u32(target, DCB_DCRDR, target->savedDCRDR);
732 if (res != ERROR_OK)
733 return res;
734
735 target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
736
737 res = adapter->layout->api->step(adapter->fd);
738
739 if (res != ERROR_OK)
740 return res;
741
742 /* registers are now invalid */
743 register_cache_invalidate(armv7m->arm.core_cache);
744
745 if (breakpoint)
746 cortex_m_set_breakpoint(target, breakpoint);
747
748 adapter_debug_entry(target);
749 target_call_event_callbacks(target, TARGET_EVENT_HALTED);
750
751 LOG_INFO("halted: PC: 0x%08x", buf_get_u32(armv7m->arm.pc->value, 0, 32));
752
753 return ERROR_OK;
754 }
755
756 static int adapter_read_memory(struct target *target, uint32_t address,
757 uint32_t size, uint32_t count,
758 uint8_t *buffer)
759 {
760 struct hl_interface_s *adapter = target_to_adapter(target);
761
762 if (!count || !buffer)
763 return ERROR_COMMAND_SYNTAX_ERROR;
764
765 LOG_DEBUG("%s 0x%08x %d %d", __func__, address, size, count);
766
767 return adapter->layout->api->read_mem(adapter->fd, address, size, count, buffer);
768 }
769
770 static int adapter_write_memory(struct target *target, uint32_t address,
771 uint32_t size, uint32_t count,
772 const uint8_t *buffer)
773 {
774 struct hl_interface_s *adapter = target_to_adapter(target);
775
776 if (!count || !buffer)
777 return ERROR_COMMAND_SYNTAX_ERROR;
778
779 LOG_DEBUG("%s 0x%08x %d %d", __func__, address, size, count);
780
781 return adapter->layout->api->write_mem(adapter->fd, address, size, count, buffer);
782 }
783
784 static const struct command_registration adapter_command_handlers[] = {
785 {
786 .chain = arm_command_handlers,
787 },
788 COMMAND_REGISTRATION_DONE
789 };
790
791 struct target_type hla_target = {
792 .name = "hla_target",
793 .deprecated_name = "stm32_stlink",
794
795 .init_target = adapter_init_target,
796 .target_create = adapter_target_create,
797 .examine = cortex_m_examine,
798 .commands = adapter_command_handlers,
799
800 .poll = adapter_poll,
801 .arch_state = armv7m_arch_state,
802
803 .target_request_data = hl_target_request_data,
804 .assert_reset = adapter_assert_reset,
805 .deassert_reset = adapter_deassert_reset,
806
807 .halt = adapter_halt,
808 .resume = adapter_resume,
809 .step = adapter_step,
810
811 .get_gdb_reg_list = armv7m_get_gdb_reg_list,
812
813 .read_memory = adapter_read_memory,
814 .write_memory = adapter_write_memory,
815 .checksum_memory = armv7m_checksum_memory,
816 .blank_check_memory = armv7m_blank_check_memory,
817
818 .run_algorithm = armv7m_run_algorithm,
819 .start_algorithm = armv7m_start_algorithm,
820 .wait_algorithm = armv7m_wait_algorithm,
821
822 .add_breakpoint = cortex_m_add_breakpoint,
823 .remove_breakpoint = cortex_m_remove_breakpoint,
824 .add_watchpoint = cortex_m_add_watchpoint,
825 .remove_watchpoint = cortex_m_remove_watchpoint,
826 };

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)