1 /***************************************************************************
2 * Copyright (C) 2015 by David Ung *
4 * This program is free software; you can redistribute it and/or modify *
5 * it under the terms of the GNU General Public License as published by *
6 * the Free Software Foundation; either version 2 of the License, or *
7 * (at your option) any later version. *
9 * This program is distributed in the hope that it will be useful, *
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
12 * GNU General Public License for more details. *
14 * You should have received a copy of the GNU General Public License *
15 * along with this program; if not, write to the *
16 * Free Software Foundation, Inc., *
18 ***************************************************************************/
24 #include "breakpoints.h"
27 #include "target_request.h"
28 #include "target_type.h"
29 #include "arm_opcodes.h"
30 #include <helper/time_support.h>
32 static int aarch64_poll(struct target
*target
);
33 static int aarch64_debug_entry(struct target
*target
);
34 static int aarch64_restore_context(struct target
*target
, bool bpwp
);
35 static int aarch64_set_breakpoint(struct target
*target
,
36 struct breakpoint
*breakpoint
, uint8_t matchmode
);
37 static int aarch64_set_context_breakpoint(struct target
*target
,
38 struct breakpoint
*breakpoint
, uint8_t matchmode
);
39 static int aarch64_set_hybrid_breakpoint(struct target
*target
,
40 struct breakpoint
*breakpoint
);
41 static int aarch64_unset_breakpoint(struct target
*target
,
42 struct breakpoint
*breakpoint
);
43 static int aarch64_mmu(struct target
*target
, int *enabled
);
44 static int aarch64_virt2phys(struct target
*target
,
45 target_addr_t virt
, target_addr_t
*phys
);
46 static int aarch64_read_apb_ab_memory(struct target
*target
,
47 uint64_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
);
48 static int aarch64_instr_write_data_r0(struct arm_dpm
*dpm
,
49 uint32_t opcode
, uint32_t data
);
51 static int aarch64_restore_system_control_reg(struct target
*target
)
53 int retval
= ERROR_OK
;
55 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
56 struct armv8_common
*armv8
= target_to_armv8(target
);
58 if (aarch64
->system_control_reg
!= aarch64
->system_control_reg_curr
) {
59 aarch64
->system_control_reg_curr
= aarch64
->system_control_reg
;
60 retval
= aarch64_instr_write_data_r0(armv8
->arm
.dpm
,
62 aarch64
->system_control_reg
);
68 /* check address before aarch64_apb read write access with mmu on
69 * remove apb predictible data abort */
70 static int aarch64_check_address(struct target
*target
, uint32_t address
)
75 /* modify system_control_reg in order to enable or disable mmu for :
76 * - virt2phys address conversion
77 * - read or write memory in phys or virt address */
78 static int aarch64_mmu_modify(struct target
*target
, int enable
)
80 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
81 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
82 int retval
= ERROR_OK
;
85 /* if mmu enabled at target stop and mmu not enable */
86 if (!(aarch64
->system_control_reg
& 0x1U
)) {
87 LOG_ERROR("trying to enable mmu on target stopped with mmu disable");
90 if (!(aarch64
->system_control_reg_curr
& 0x1U
)) {
91 aarch64
->system_control_reg_curr
|= 0x1U
;
92 retval
= aarch64_instr_write_data_r0(armv8
->arm
.dpm
,
94 aarch64
->system_control_reg_curr
);
97 if (aarch64
->system_control_reg_curr
& 0x4U
) {
98 /* data cache is active */
99 aarch64
->system_control_reg_curr
&= ~0x4U
;
100 /* flush data cache armv7 function to be called */
101 if (armv8
->armv8_mmu
.armv8_cache
.flush_all_data_cache
)
102 armv8
->armv8_mmu
.armv8_cache
.flush_all_data_cache(target
);
104 if ((aarch64
->system_control_reg_curr
& 0x1U
)) {
105 aarch64
->system_control_reg_curr
&= ~0x1U
;
106 retval
= aarch64_instr_write_data_r0(armv8
->arm
.dpm
,
108 aarch64
->system_control_reg_curr
);
115 * Basic debug access, very low level assumes state is saved
117 static int aarch64_init_debug_access(struct target
*target
)
119 struct armv8_common
*armv8
= target_to_armv8(target
);
125 /* Unlocking the debug registers for modification
126 * The debugport might be uninitialised so try twice */
127 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
128 armv8
->debug_base
+ CPUDBG_LOCKACCESS
, 0xC5ACCE55);
129 if (retval
!= ERROR_OK
) {
131 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
132 armv8
->debug_base
+ CPUDBG_LOCKACCESS
, 0xC5ACCE55);
133 if (retval
== ERROR_OK
)
134 LOG_USER("Locking debug access failed on first, but succeeded on second try.");
136 if (retval
!= ERROR_OK
)
138 /* Clear Sticky Power Down status Bit in PRSR to enable access to
139 the registers in the Core Power Domain */
140 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
141 armv8
->debug_base
+ CPUDBG_PRSR
, &dummy
);
142 if (retval
!= ERROR_OK
)
145 /* Enabling of instruction execution in debug mode is done in debug_entry code */
147 /* Resync breakpoint registers */
149 /* Since this is likely called from init or reset, update target state information*/
150 return aarch64_poll(target
);
153 /* To reduce needless round-trips, pass in a pointer to the current
154 * DSCR value. Initialize it to zero if you just need to know the
155 * value on return from this function; or DSCR_INSTR_COMP if you
156 * happen to know that no instruction is pending.
158 static int aarch64_exec_opcode(struct target
*target
,
159 uint32_t opcode
, uint32_t *dscr_p
)
163 struct armv8_common
*armv8
= target_to_armv8(target
);
164 dscr
= dscr_p
? *dscr_p
: 0;
166 LOG_DEBUG("exec opcode 0x%08" PRIx32
, opcode
);
168 /* Wait for InstrCompl bit to be set */
169 long long then
= timeval_ms();
170 while ((dscr
& DSCR_INSTR_COMP
) == 0) {
171 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
172 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
173 if (retval
!= ERROR_OK
) {
174 LOG_ERROR("Could not read DSCR register, opcode = 0x%08" PRIx32
, opcode
);
177 if (timeval_ms() > then
+ 1000) {
178 LOG_ERROR("Timeout waiting for aarch64_exec_opcode");
183 retval
= mem_ap_write_u32(armv8
->debug_ap
,
184 armv8
->debug_base
+ CPUDBG_ITR
, opcode
);
185 if (retval
!= ERROR_OK
)
190 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
191 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
192 if (retval
!= ERROR_OK
) {
193 LOG_ERROR("Could not read DSCR register");
196 if (timeval_ms() > then
+ 1000) {
197 LOG_ERROR("Timeout waiting for aarch64_exec_opcode");
200 } while ((dscr
& DSCR_INSTR_COMP
) == 0); /* Wait for InstrCompl bit to be set */
208 /* Write to memory mapped registers directly with no cache or mmu handling */
209 static int aarch64_dap_write_memap_register_u32(struct target
*target
,
214 struct armv8_common
*armv8
= target_to_armv8(target
);
216 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
, address
, value
);
222 * AARCH64 implementation of Debug Programmer's Model
224 * NOTE the invariant: these routines return with DSCR_INSTR_COMP set,
225 * so there's no need to poll for it before executing an instruction.
227 * NOTE that in several of these cases the "stall" mode might be useful.
228 * It'd let us queue a few operations together... prepare/finish might
229 * be the places to enable/disable that mode.
232 static inline struct aarch64_common
*dpm_to_a8(struct arm_dpm
*dpm
)
234 return container_of(dpm
, struct aarch64_common
, armv8_common
.dpm
);
237 static int aarch64_write_dcc(struct aarch64_common
*a8
, uint32_t data
)
239 LOG_DEBUG("write DCC 0x%08" PRIx32
, data
);
240 return mem_ap_write_u32(a8
->armv8_common
.debug_ap
,
241 a8
->armv8_common
.debug_base
+ CPUDBG_DTRRX
, data
);
244 static int aarch64_write_dcc_64(struct aarch64_common
*a8
, uint64_t data
)
247 LOG_DEBUG("write DCC 0x%08" PRIx32
, (unsigned)data
);
248 LOG_DEBUG("write DCC 0x%08" PRIx32
, (unsigned)(data
>> 32));
249 ret
= mem_ap_write_u32(a8
->armv8_common
.debug_ap
,
250 a8
->armv8_common
.debug_base
+ CPUDBG_DTRRX
, data
);
251 ret
+= mem_ap_write_u32(a8
->armv8_common
.debug_ap
,
252 a8
->armv8_common
.debug_base
+ CPUDBG_DTRTX
, data
>> 32);
256 static int aarch64_read_dcc(struct aarch64_common
*a8
, uint32_t *data
,
259 uint32_t dscr
= DSCR_INSTR_COMP
;
265 /* Wait for DTRRXfull */
266 long long then
= timeval_ms();
267 while ((dscr
& DSCR_DTR_TX_FULL
) == 0) {
268 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
269 a8
->armv8_common
.debug_base
+ CPUDBG_DSCR
,
271 if (retval
!= ERROR_OK
)
273 if (timeval_ms() > then
+ 1000) {
274 LOG_ERROR("Timeout waiting for read dcc");
279 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
280 a8
->armv8_common
.debug_base
+ CPUDBG_DTRTX
,
282 if (retval
!= ERROR_OK
)
284 LOG_DEBUG("read DCC 0x%08" PRIx32
, *data
);
291 static int aarch64_read_dcc_64(struct aarch64_common
*a8
, uint64_t *data
,
294 uint32_t dscr
= DSCR_INSTR_COMP
;
301 /* Wait for DTRRXfull */
302 long long then
= timeval_ms();
303 while ((dscr
& DSCR_DTR_TX_FULL
) == 0) {
304 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
305 a8
->armv8_common
.debug_base
+ CPUDBG_DSCR
,
307 if (retval
!= ERROR_OK
)
309 if (timeval_ms() > then
+ 1000) {
310 LOG_ERROR("Timeout waiting for read dcc");
315 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
316 a8
->armv8_common
.debug_base
+ CPUDBG_DTRTX
,
318 if (retval
!= ERROR_OK
)
321 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
322 a8
->armv8_common
.debug_base
+ CPUDBG_DTRRX
,
324 if (retval
!= ERROR_OK
)
327 *data
= *(uint32_t *)data
| (uint64_t)higher
<< 32;
328 LOG_DEBUG("read DCC 0x%16.16" PRIx64
, *data
);
336 static int aarch64_dpm_prepare(struct arm_dpm
*dpm
)
338 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
342 /* set up invariant: INSTR_COMP is set after ever DPM operation */
343 long long then
= timeval_ms();
345 retval
= mem_ap_read_atomic_u32(a8
->armv8_common
.debug_ap
,
346 a8
->armv8_common
.debug_base
+ CPUDBG_DSCR
,
348 if (retval
!= ERROR_OK
)
350 if ((dscr
& DSCR_INSTR_COMP
) != 0)
352 if (timeval_ms() > then
+ 1000) {
353 LOG_ERROR("Timeout waiting for dpm prepare");
358 /* this "should never happen" ... */
359 if (dscr
& DSCR_DTR_RX_FULL
) {
360 LOG_ERROR("DSCR_DTR_RX_FULL, dscr 0x%08" PRIx32
, dscr
);
362 retval
= aarch64_exec_opcode(
363 a8
->armv8_common
.arm
.target
,
366 if (retval
!= ERROR_OK
)
373 static int aarch64_dpm_finish(struct arm_dpm
*dpm
)
375 /* REVISIT what could be done here? */
379 static int aarch64_instr_write_data_dcc(struct arm_dpm
*dpm
,
380 uint32_t opcode
, uint32_t data
)
382 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
384 uint32_t dscr
= DSCR_INSTR_COMP
;
386 retval
= aarch64_write_dcc(a8
, data
);
387 if (retval
!= ERROR_OK
)
390 return aarch64_exec_opcode(
391 a8
->armv8_common
.arm
.target
,
396 static int aarch64_instr_write_data_dcc_64(struct arm_dpm
*dpm
,
397 uint32_t opcode
, uint64_t data
)
399 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
401 uint32_t dscr
= DSCR_INSTR_COMP
;
403 retval
= aarch64_write_dcc_64(a8
, data
);
404 if (retval
!= ERROR_OK
)
407 return aarch64_exec_opcode(
408 a8
->armv8_common
.arm
.target
,
413 static int aarch64_instr_write_data_r0(struct arm_dpm
*dpm
,
414 uint32_t opcode
, uint32_t data
)
416 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
417 uint32_t dscr
= DSCR_INSTR_COMP
;
420 retval
= aarch64_write_dcc(a8
, data
);
421 if (retval
!= ERROR_OK
)
424 retval
= aarch64_exec_opcode(
425 a8
->armv8_common
.arm
.target
,
428 if (retval
!= ERROR_OK
)
431 /* then the opcode, taking data from R0 */
432 retval
= aarch64_exec_opcode(
433 a8
->armv8_common
.arm
.target
,
440 static int aarch64_instr_write_data_r0_64(struct arm_dpm
*dpm
,
441 uint32_t opcode
, uint64_t data
)
443 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
444 uint32_t dscr
= DSCR_INSTR_COMP
;
447 retval
= aarch64_write_dcc_64(a8
, data
);
448 if (retval
!= ERROR_OK
)
451 retval
= aarch64_exec_opcode(
452 a8
->armv8_common
.arm
.target
,
455 if (retval
!= ERROR_OK
)
458 /* then the opcode, taking data from R0 */
459 retval
= aarch64_exec_opcode(
460 a8
->armv8_common
.arm
.target
,
467 static int aarch64_instr_cpsr_sync(struct arm_dpm
*dpm
)
469 struct target
*target
= dpm
->arm
->target
;
470 uint32_t dscr
= DSCR_INSTR_COMP
;
472 /* "Prefetch flush" after modifying execution status in CPSR */
473 return aarch64_exec_opcode(target
,
474 ARMV4_5_MCR(15, 0, 0, 7, 5, 4),
478 static int aarch64_instr_read_data_dcc(struct arm_dpm
*dpm
,
479 uint32_t opcode
, uint32_t *data
)
481 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
483 uint32_t dscr
= DSCR_INSTR_COMP
;
485 /* the opcode, writing data to DCC */
486 retval
= aarch64_exec_opcode(
487 a8
->armv8_common
.arm
.target
,
490 if (retval
!= ERROR_OK
)
493 return aarch64_read_dcc(a8
, data
, &dscr
);
496 static int aarch64_instr_read_data_dcc_64(struct arm_dpm
*dpm
,
497 uint32_t opcode
, uint64_t *data
)
499 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
501 uint32_t dscr
= DSCR_INSTR_COMP
;
503 /* the opcode, writing data to DCC */
504 retval
= aarch64_exec_opcode(
505 a8
->armv8_common
.arm
.target
,
508 if (retval
!= ERROR_OK
)
511 return aarch64_read_dcc_64(a8
, data
, &dscr
);
514 static int aarch64_instr_read_data_r0(struct arm_dpm
*dpm
,
515 uint32_t opcode
, uint32_t *data
)
517 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
518 uint32_t dscr
= DSCR_INSTR_COMP
;
521 /* the opcode, writing data to R0 */
522 retval
= aarch64_exec_opcode(
523 a8
->armv8_common
.arm
.target
,
526 if (retval
!= ERROR_OK
)
529 /* write R0 to DCC */
530 retval
= aarch64_exec_opcode(
531 a8
->armv8_common
.arm
.target
,
532 0xd5130400, /* msr dbgdtr_el0, x0 */
534 if (retval
!= ERROR_OK
)
537 return aarch64_read_dcc(a8
, data
, &dscr
);
540 static int aarch64_instr_read_data_r0_64(struct arm_dpm
*dpm
,
541 uint32_t opcode
, uint64_t *data
)
543 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
544 uint32_t dscr
= DSCR_INSTR_COMP
;
547 /* the opcode, writing data to R0 */
548 retval
= aarch64_exec_opcode(
549 a8
->armv8_common
.arm
.target
,
552 if (retval
!= ERROR_OK
)
555 /* write R0 to DCC */
556 retval
= aarch64_exec_opcode(
557 a8
->armv8_common
.arm
.target
,
558 0xd5130400, /* msr dbgdtr_el0, x0 */
560 if (retval
!= ERROR_OK
)
563 return aarch64_read_dcc_64(a8
, data
, &dscr
);
566 static int aarch64_bpwp_enable(struct arm_dpm
*dpm
, unsigned index_t
,
567 uint32_t addr
, uint32_t control
)
569 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
570 uint32_t vr
= a8
->armv8_common
.debug_base
;
571 uint32_t cr
= a8
->armv8_common
.debug_base
;
575 case 0 ... 15: /* breakpoints */
576 vr
+= CPUDBG_BVR_BASE
;
577 cr
+= CPUDBG_BCR_BASE
;
579 case 16 ... 31: /* watchpoints */
580 vr
+= CPUDBG_WVR_BASE
;
581 cr
+= CPUDBG_WCR_BASE
;
590 LOG_DEBUG("A8: bpwp enable, vr %08x cr %08x",
591 (unsigned) vr
, (unsigned) cr
);
593 retval
= aarch64_dap_write_memap_register_u32(dpm
->arm
->target
,
595 if (retval
!= ERROR_OK
)
597 retval
= aarch64_dap_write_memap_register_u32(dpm
->arm
->target
,
602 static int aarch64_bpwp_disable(struct arm_dpm
*dpm
, unsigned index_t
)
607 struct aarch64_common
*a8
= dpm_to_a8(dpm
);
612 cr
= a8
->armv8_common
.debug_base
+ CPUDBG_BCR_BASE
;
615 cr
= a8
->armv8_common
.debug_base
+ CPUDBG_WCR_BASE
;
623 LOG_DEBUG("A8: bpwp disable, cr %08x", (unsigned) cr
);
625 /* clear control register */
626 return aarch64_dap_write_memap_register_u32(dpm
->arm
->target
, cr
, 0);
630 static int aarch64_dpm_setup(struct aarch64_common
*a8
, uint32_t debug
)
632 struct arm_dpm
*dpm
= &a8
->armv8_common
.dpm
;
635 dpm
->arm
= &a8
->armv8_common
.arm
;
638 dpm
->prepare
= aarch64_dpm_prepare
;
639 dpm
->finish
= aarch64_dpm_finish
;
641 dpm
->instr_write_data_dcc
= aarch64_instr_write_data_dcc
;
642 dpm
->instr_write_data_dcc_64
= aarch64_instr_write_data_dcc_64
;
643 dpm
->instr_write_data_r0
= aarch64_instr_write_data_r0
;
644 dpm
->instr_write_data_r0_64
= aarch64_instr_write_data_r0_64
;
645 dpm
->instr_cpsr_sync
= aarch64_instr_cpsr_sync
;
647 dpm
->instr_read_data_dcc
= aarch64_instr_read_data_dcc
;
648 dpm
->instr_read_data_dcc_64
= aarch64_instr_read_data_dcc_64
;
649 dpm
->instr_read_data_r0
= aarch64_instr_read_data_r0
;
650 dpm
->instr_read_data_r0_64
= aarch64_instr_read_data_r0_64
;
652 dpm
->arm_reg_current
= armv8_reg_current
;
654 dpm
->bpwp_enable
= aarch64_bpwp_enable
;
655 dpm
->bpwp_disable
= aarch64_bpwp_disable
;
657 retval
= arm_dpm_setup(dpm
);
658 if (retval
== ERROR_OK
)
659 retval
= arm_dpm_initialize(dpm
);
663 static struct target
*get_aarch64(struct target
*target
, int32_t coreid
)
665 struct target_list
*head
;
669 while (head
!= (struct target_list
*)NULL
) {
671 if ((curr
->coreid
== coreid
) && (curr
->state
== TARGET_HALTED
))
677 static int aarch64_halt(struct target
*target
);
679 static int aarch64_halt_smp(struct target
*target
)
682 struct target_list
*head
;
685 while (head
!= (struct target_list
*)NULL
) {
687 if ((curr
!= target
) && (curr
->state
!= TARGET_HALTED
))
688 retval
+= aarch64_halt(curr
);
694 static int update_halt_gdb(struct target
*target
)
697 if (target
->gdb_service
&& target
->gdb_service
->core
[0] == -1) {
698 target
->gdb_service
->target
= target
;
699 target
->gdb_service
->core
[0] = target
->coreid
;
700 retval
+= aarch64_halt_smp(target
);
706 * Cortex-A8 Run control
709 static int aarch64_poll(struct target
*target
)
711 int retval
= ERROR_OK
;
713 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
714 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
715 enum target_state prev_target_state
= target
->state
;
716 /* toggle to another core is done by gdb as follow */
717 /* maint packet J core_id */
719 /* the next polling trigger an halt event sent to gdb */
720 if ((target
->state
== TARGET_HALTED
) && (target
->smp
) &&
721 (target
->gdb_service
) &&
722 (target
->gdb_service
->target
== NULL
)) {
723 target
->gdb_service
->target
=
724 get_aarch64(target
, target
->gdb_service
->core
[1]);
725 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
728 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
729 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
730 if (retval
!= ERROR_OK
)
732 aarch64
->cpudbg_dscr
= dscr
;
734 if (DSCR_RUN_MODE(dscr
) == (DSCR_CORE_HALTED
| DSCR_CORE_RESTARTED
)) {
735 if (prev_target_state
!= TARGET_HALTED
) {
736 /* We have a halting debug event */
737 LOG_DEBUG("Target halted");
738 target
->state
= TARGET_HALTED
;
739 if ((prev_target_state
== TARGET_RUNNING
)
740 || (prev_target_state
== TARGET_UNKNOWN
)
741 || (prev_target_state
== TARGET_RESET
)) {
742 retval
= aarch64_debug_entry(target
);
743 if (retval
!= ERROR_OK
)
746 retval
= update_halt_gdb(target
);
747 if (retval
!= ERROR_OK
)
750 target_call_event_callbacks(target
,
751 TARGET_EVENT_HALTED
);
753 if (prev_target_state
== TARGET_DEBUG_RUNNING
) {
756 retval
= aarch64_debug_entry(target
);
757 if (retval
!= ERROR_OK
)
760 retval
= update_halt_gdb(target
);
761 if (retval
!= ERROR_OK
)
765 target_call_event_callbacks(target
,
766 TARGET_EVENT_DEBUG_HALTED
);
769 } else if (DSCR_RUN_MODE(dscr
) == DSCR_CORE_RESTARTED
)
770 target
->state
= TARGET_RUNNING
;
772 LOG_DEBUG("Unknown target state dscr = 0x%08" PRIx32
, dscr
);
773 target
->state
= TARGET_UNKNOWN
;
779 static int aarch64_halt(struct target
*target
)
781 int retval
= ERROR_OK
;
783 struct armv8_common
*armv8
= target_to_armv8(target
);
785 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
786 armv8
->debug_base
+ 0x10000 + 0, &dscr
);
787 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
788 armv8
->debug_base
+ 0x10000 + 0, 1);
789 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
790 armv8
->debug_base
+ 0x10000 + 0, &dscr
);
792 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
793 armv8
->debug_base
+ 0x10000 + 0x140, &dscr
);
794 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
795 armv8
->debug_base
+ 0x10000 + 0x140, 6);
796 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
797 armv8
->debug_base
+ 0x10000 + 0x140, &dscr
);
799 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
800 armv8
->debug_base
+ 0x10000 + 0xa0, &dscr
);
801 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
802 armv8
->debug_base
+ 0x10000 + 0xa0, 5);
803 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
804 armv8
->debug_base
+ 0x10000 + 0xa0, &dscr
);
806 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
807 armv8
->debug_base
+ 0x10000 + 0xa4, &dscr
);
808 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
809 armv8
->debug_base
+ 0x10000 + 0xa4, 2);
810 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
811 armv8
->debug_base
+ 0x10000 + 0xa4, &dscr
);
813 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
814 armv8
->debug_base
+ 0x10000 + 0x20, &dscr
);
815 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
816 armv8
->debug_base
+ 0x10000 + 0x20, 4);
817 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
818 armv8
->debug_base
+ 0x10000 + 0x20, &dscr
);
821 * enter halting debug mode
823 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
824 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
825 if (retval
!= ERROR_OK
)
829 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
830 armv8
->debug_base
+ 0x10000 + 0x134, &dscr
);
832 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
833 armv8
->debug_base
+ 0x10000 + 0x1c, &dscr
);
834 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
835 armv8
->debug_base
+ 0x10000 + 0x1c, 1);
836 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
837 armv8
->debug_base
+ 0x10000 + 0x1c, &dscr
);
840 long long then
= timeval_ms();
842 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
843 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
844 if (retval
!= ERROR_OK
)
846 if ((dscr
& DSCR_CORE_HALTED
) != 0)
848 if (timeval_ms() > then
+ 1000) {
849 LOG_ERROR("Timeout waiting for halt");
854 target
->debug_reason
= DBG_REASON_DBGRQ
;
859 static int aarch64_internal_restore(struct target
*target
, int current
,
860 uint64_t *address
, int handle_breakpoints
, int debug_execution
)
862 struct armv8_common
*armv8
= target_to_armv8(target
);
863 struct arm
*arm
= &armv8
->arm
;
867 if (!debug_execution
)
868 target_free_all_working_areas(target
);
870 /* current = 1: continue on current pc, otherwise continue at <address> */
871 resume_pc
= buf_get_u64(arm
->pc
->value
, 0, 64);
873 resume_pc
= *address
;
875 *address
= resume_pc
;
877 /* Make sure that the Armv7 gdb thumb fixups does not
878 * kill the return address
880 switch (arm
->core_state
) {
882 case ARM_STATE_AARCH64
:
883 resume_pc
&= 0xFFFFFFFFFFFFFFFC;
885 case ARM_STATE_THUMB
:
886 case ARM_STATE_THUMB_EE
:
887 /* When the return address is loaded into PC
888 * bit 0 must be 1 to stay in Thumb state
892 case ARM_STATE_JAZELLE
:
893 LOG_ERROR("How do I resume into Jazelle state??");
896 LOG_DEBUG("resume pc = 0x%16" PRIx64
, resume_pc
);
897 buf_set_u64(arm
->pc
->value
, 0, 64, resume_pc
);
901 /* restore dpm_mode at system halt */
902 dpm_modeswitch(&armv8
->dpm
, ARM_MODE_ANY
);
904 /* called it now before restoring context because it uses cpu
905 * register r0 for restoring system control register */
906 retval
= aarch64_restore_system_control_reg(target
);
907 if (retval
!= ERROR_OK
)
909 retval
= aarch64_restore_context(target
, handle_breakpoints
);
910 if (retval
!= ERROR_OK
)
912 target
->debug_reason
= DBG_REASON_NOTHALTED
;
913 target
->state
= TARGET_RUNNING
;
915 /* registers are now invalid */
916 register_cache_invalidate(arm
->core_cache
);
919 /* the front-end may request us not to handle breakpoints */
920 if (handle_breakpoints
) {
921 /* Single step past breakpoint at current address */
922 breakpoint
= breakpoint_find(target
, resume_pc
);
924 LOG_DEBUG("unset breakpoint at 0x%8.8x", breakpoint
->address
);
925 cortex_m3_unset_breakpoint(target
, breakpoint
);
926 cortex_m3_single_step_core(target
);
927 cortex_m3_set_breakpoint(target
, breakpoint
);
935 static int aarch64_internal_restart(struct target
*target
)
937 struct armv8_common
*armv8
= target_to_armv8(target
);
938 struct arm
*arm
= &armv8
->arm
;
942 * * Restart core and wait for it to be started. Clear ITRen and sticky
943 * * exception flags: see ARMv7 ARM, C5.9.
945 * REVISIT: for single stepping, we probably want to
946 * disable IRQs by default, with optional override...
949 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
950 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
951 if (retval
!= ERROR_OK
)
954 if ((dscr
& DSCR_INSTR_COMP
) == 0)
955 LOG_ERROR("DSCR InstrCompl must be set before leaving debug!");
957 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
958 armv8
->debug_base
+ CPUDBG_DSCR
, dscr
& ~DSCR_ITR_EN
);
959 if (retval
!= ERROR_OK
)
962 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
963 armv8
->debug_base
+ CPUDBG_DRCR
, DRCR_RESTART
|
964 DRCR_CLEAR_EXCEPTIONS
);
965 if (retval
!= ERROR_OK
)
968 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
969 armv8
->debug_base
+ 0x10000 + 0x10, 1);
970 if (retval
!= ERROR_OK
)
973 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
974 armv8
->debug_base
+ 0x10000 + 0x1c, 2);
975 if (retval
!= ERROR_OK
)
978 long long then
= timeval_ms();
980 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
981 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
982 if (retval
!= ERROR_OK
)
984 if ((dscr
& DSCR_CORE_RESTARTED
) != 0)
986 if (timeval_ms() > then
+ 1000) {
987 LOG_ERROR("Timeout waiting for resume");
992 target
->debug_reason
= DBG_REASON_NOTHALTED
;
993 target
->state
= TARGET_RUNNING
;
995 /* registers are now invalid */
996 register_cache_invalidate(arm
->core_cache
);
1001 static int aarch64_restore_smp(struct target
*target
, int handle_breakpoints
)
1004 struct target_list
*head
;
1005 struct target
*curr
;
1007 head
= target
->head
;
1008 while (head
!= (struct target_list
*)NULL
) {
1009 curr
= head
->target
;
1010 if ((curr
!= target
) && (curr
->state
!= TARGET_RUNNING
)) {
1011 /* resume current address , not in step mode */
1012 retval
+= aarch64_internal_restore(curr
, 1, &address
,
1013 handle_breakpoints
, 0);
1014 retval
+= aarch64_internal_restart(curr
);
1022 static int aarch64_resume(struct target
*target
, int current
,
1023 target_addr_t address
, int handle_breakpoints
, int debug_execution
)
1026 uint64_t resume_addr
;
1029 LOG_DEBUG("resuming with custom address not supported");
1033 /* dummy resume for smp toggle in order to reduce gdb impact */
1034 if ((target
->smp
) && (target
->gdb_service
->core
[1] != -1)) {
1035 /* simulate a start and halt of target */
1036 target
->gdb_service
->target
= NULL
;
1037 target
->gdb_service
->core
[0] = target
->gdb_service
->core
[1];
1038 /* fake resume at next poll we play the target core[1], see poll*/
1039 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1042 aarch64_internal_restore(target
, current
, &resume_addr
, handle_breakpoints
, debug_execution
);
1044 target
->gdb_service
->core
[0] = -1;
1045 retval
= aarch64_restore_smp(target
, handle_breakpoints
);
1046 if (retval
!= ERROR_OK
)
1049 aarch64_internal_restart(target
);
1051 if (!debug_execution
) {
1052 target
->state
= TARGET_RUNNING
;
1053 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1054 LOG_DEBUG("target resumed at 0x%" PRIx64
, resume_addr
);
1056 target
->state
= TARGET_DEBUG_RUNNING
;
1057 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
1058 LOG_DEBUG("target debug resumed at 0x%" PRIx64
, resume_addr
);
1064 static int aarch64_debug_entry(struct target
*target
)
1067 int retval
= ERROR_OK
;
1068 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1069 struct armv8_common
*armv8
= target_to_armv8(target
);
1071 LOG_DEBUG("dscr = 0x%08" PRIx32
, aarch64
->cpudbg_dscr
);
1073 /* REVISIT surely we should not re-read DSCR !! */
1074 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1075 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1076 if (retval
!= ERROR_OK
)
1079 /* REVISIT see A8 TRM 12.11.4 steps 2..3 -- make sure that any
1080 * imprecise data aborts get discarded by issuing a Data
1081 * Synchronization Barrier: ARMV4_5_MCR(15, 0, 0, 7, 10, 4).
1084 /* Enable the ITR execution once we are in debug mode */
1085 dscr
|= DSCR_ITR_EN
;
1086 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1087 armv8
->debug_base
+ CPUDBG_DSCR
, dscr
);
1088 if (retval
!= ERROR_OK
)
1091 /* Examine debug reason */
1092 arm_dpm_report_dscr(&armv8
->dpm
, aarch64
->cpudbg_dscr
);
1094 /* save address of instruction that triggered the watchpoint? */
1095 if (target
->debug_reason
== DBG_REASON_WATCHPOINT
) {
1098 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1099 armv8
->debug_base
+ CPUDBG_WFAR
,
1101 if (retval
!= ERROR_OK
)
1103 arm_dpm_report_wfar(&armv8
->dpm
, wfar
);
1106 retval
= arm_dpm_read_current_registers_64(&armv8
->dpm
);
1108 if (armv8
->post_debug_entry
) {
1109 retval
= armv8
->post_debug_entry(target
);
1110 if (retval
!= ERROR_OK
)
1117 static int aarch64_post_debug_entry(struct target
*target
)
1119 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1120 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1121 struct armv8_mmu_common
*armv8_mmu
= &armv8
->armv8_mmu
;
1122 uint32_t sctlr_el1
= 0;
1125 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1126 armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1127 retval
= aarch64_instr_read_data_r0(armv8
->arm
.dpm
,
1128 0xd5381000, &sctlr_el1
);
1129 if (retval
!= ERROR_OK
)
1132 LOG_DEBUG("sctlr_el1 = %#8.8x", sctlr_el1
);
1133 aarch64
->system_control_reg
= sctlr_el1
;
1134 aarch64
->system_control_reg_curr
= sctlr_el1
;
1135 aarch64
->curr_mode
= armv8
->arm
.core_mode
;
1137 armv8_mmu
->mmu_enabled
= sctlr_el1
& 0x1U
? 1 : 0;
1138 armv8_mmu
->armv8_cache
.d_u_cache_enabled
= sctlr_el1
& 0x4U
? 1 : 0;
1139 armv8_mmu
->armv8_cache
.i_cache_enabled
= sctlr_el1
& 0x1000U
? 1 : 0;
1142 if (armv8
->armv8_mmu
.armv8_cache
.ctype
== -1)
1143 armv8_identify_cache(target
);
1149 static int aarch64_step(struct target
*target
, int current
, target_addr_t address
,
1150 int handle_breakpoints
)
1152 struct armv8_common
*armv8
= target_to_armv8(target
);
1153 struct arm
*arm
= &armv8
->arm
;
1154 struct breakpoint
*breakpoint
= NULL
;
1155 struct breakpoint stepbreakpoint
;
1159 if (target
->state
!= TARGET_HALTED
) {
1160 LOG_WARNING("target not halted");
1161 return ERROR_TARGET_NOT_HALTED
;
1164 /* current = 1: continue on current pc, otherwise continue at <address> */
1167 buf_set_u64(r
->value
, 0, 64, address
);
1169 address
= buf_get_u64(r
->value
, 0, 64);
1171 /* The front-end may request us not to handle breakpoints.
1172 * But since Cortex-A8 uses breakpoint for single step,
1173 * we MUST handle breakpoints.
1175 handle_breakpoints
= 1;
1176 if (handle_breakpoints
) {
1177 breakpoint
= breakpoint_find(target
, address
);
1179 aarch64_unset_breakpoint(target
, breakpoint
);
1182 /* Setup single step breakpoint */
1183 stepbreakpoint
.address
= address
;
1184 stepbreakpoint
.length
= 4;
1185 stepbreakpoint
.type
= BKPT_HARD
;
1186 stepbreakpoint
.set
= 0;
1188 /* Break on IVA mismatch */
1189 aarch64_set_breakpoint(target
, &stepbreakpoint
, 0x04);
1191 target
->debug_reason
= DBG_REASON_SINGLESTEP
;
1193 retval
= aarch64_resume(target
, 1, address
, 0, 0);
1194 if (retval
!= ERROR_OK
)
1197 long long then
= timeval_ms();
1198 while (target
->state
!= TARGET_HALTED
) {
1199 retval
= aarch64_poll(target
);
1200 if (retval
!= ERROR_OK
)
1202 if (timeval_ms() > then
+ 1000) {
1203 LOG_ERROR("timeout waiting for target halt");
1208 aarch64_unset_breakpoint(target
, &stepbreakpoint
);
1210 target
->debug_reason
= DBG_REASON_BREAKPOINT
;
1213 aarch64_set_breakpoint(target
, breakpoint
, 0);
1215 if (target
->state
!= TARGET_HALTED
)
1216 LOG_DEBUG("target stepped");
1221 static int aarch64_restore_context(struct target
*target
, bool bpwp
)
1223 struct armv8_common
*armv8
= target_to_armv8(target
);
1227 if (armv8
->pre_restore_context
)
1228 armv8
->pre_restore_context(target
);
1230 return arm_dpm_write_dirty_registers(&armv8
->dpm
, bpwp
);
1236 * Cortex-A8 Breakpoint and watchpoint functions
1239 /* Setup hardware Breakpoint Register Pair */
1240 static int aarch64_set_breakpoint(struct target
*target
,
1241 struct breakpoint
*breakpoint
, uint8_t matchmode
)
1246 uint8_t byte_addr_select
= 0x0F;
1247 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1248 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1249 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1251 if (breakpoint
->set
) {
1252 LOG_WARNING("breakpoint already set");
1256 if (breakpoint
->type
== BKPT_HARD
) {
1258 while (brp_list
[brp_i
].used
&& (brp_i
< aarch64
->brp_num
))
1260 if (brp_i
>= aarch64
->brp_num
) {
1261 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1262 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1264 breakpoint
->set
= brp_i
+ 1;
1265 if (breakpoint
->length
== 2)
1266 byte_addr_select
= (3 << (breakpoint
->address
& 0x02));
1267 control
= ((matchmode
& 0x7) << 20)
1269 | (byte_addr_select
<< 5)
1271 brp_list
[brp_i
].used
= 1;
1272 brp_list
[brp_i
].value
= breakpoint
->address
& 0xFFFFFFFFFFFFFFFC;
1273 brp_list
[brp_i
].control
= control
;
1274 bpt_value
= brp_list
[brp_i
].value
;
1276 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1277 + CPUDBG_BVR_BASE
+ 16 * brp_list
[brp_i
].BRPn
,
1278 (uint32_t)(bpt_value
& 0xFFFFFFFF));
1279 if (retval
!= ERROR_OK
)
1281 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1282 + CPUDBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_i
].BRPn
,
1283 (uint32_t)(bpt_value
>> 32));
1284 if (retval
!= ERROR_OK
)
1287 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1288 + CPUDBG_BCR_BASE
+ 16 * brp_list
[brp_i
].BRPn
,
1289 brp_list
[brp_i
].control
);
1290 if (retval
!= ERROR_OK
)
1292 LOG_DEBUG("brp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1293 brp_list
[brp_i
].control
,
1294 brp_list
[brp_i
].value
);
1296 } else if (breakpoint
->type
== BKPT_SOFT
) {
1298 buf_set_u32(code
, 0, 32, 0xD4400000);
1300 retval
= target_read_memory(target
,
1301 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1302 breakpoint
->length
, 1,
1303 breakpoint
->orig_instr
);
1304 if (retval
!= ERROR_OK
)
1306 retval
= target_write_memory(target
,
1307 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1308 breakpoint
->length
, 1, code
);
1309 if (retval
!= ERROR_OK
)
1311 breakpoint
->set
= 0x11; /* Any nice value but 0 */
1317 static int aarch64_set_context_breakpoint(struct target
*target
,
1318 struct breakpoint
*breakpoint
, uint8_t matchmode
)
1320 int retval
= ERROR_FAIL
;
1323 uint8_t byte_addr_select
= 0x0F;
1324 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1325 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1326 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1328 if (breakpoint
->set
) {
1329 LOG_WARNING("breakpoint already set");
1332 /*check available context BRPs*/
1333 while ((brp_list
[brp_i
].used
||
1334 (brp_list
[brp_i
].type
!= BRP_CONTEXT
)) && (brp_i
< aarch64
->brp_num
))
1337 if (brp_i
>= aarch64
->brp_num
) {
1338 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1342 breakpoint
->set
= brp_i
+ 1;
1343 control
= ((matchmode
& 0x7) << 20)
1344 | (byte_addr_select
<< 5)
1346 brp_list
[brp_i
].used
= 1;
1347 brp_list
[brp_i
].value
= (breakpoint
->asid
);
1348 brp_list
[brp_i
].control
= control
;
1349 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1350 + CPUDBG_BVR_BASE
+ 4 * brp_list
[brp_i
].BRPn
,
1351 brp_list
[brp_i
].value
);
1352 if (retval
!= ERROR_OK
)
1354 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1355 + CPUDBG_BCR_BASE
+ 4 * brp_list
[brp_i
].BRPn
,
1356 brp_list
[brp_i
].control
);
1357 if (retval
!= ERROR_OK
)
1359 LOG_DEBUG("brp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1360 brp_list
[brp_i
].control
,
1361 brp_list
[brp_i
].value
);
1366 static int aarch64_set_hybrid_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1368 int retval
= ERROR_FAIL
;
1369 int brp_1
= 0; /* holds the contextID pair */
1370 int brp_2
= 0; /* holds the IVA pair */
1371 uint32_t control_CTX
, control_IVA
;
1372 uint8_t CTX_byte_addr_select
= 0x0F;
1373 uint8_t IVA_byte_addr_select
= 0x0F;
1374 uint8_t CTX_machmode
= 0x03;
1375 uint8_t IVA_machmode
= 0x01;
1376 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1377 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1378 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1380 if (breakpoint
->set
) {
1381 LOG_WARNING("breakpoint already set");
1384 /*check available context BRPs*/
1385 while ((brp_list
[brp_1
].used
||
1386 (brp_list
[brp_1
].type
!= BRP_CONTEXT
)) && (brp_1
< aarch64
->brp_num
))
1389 printf("brp(CTX) found num: %d\n", brp_1
);
1390 if (brp_1
>= aarch64
->brp_num
) {
1391 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1395 while ((brp_list
[brp_2
].used
||
1396 (brp_list
[brp_2
].type
!= BRP_NORMAL
)) && (brp_2
< aarch64
->brp_num
))
1399 printf("brp(IVA) found num: %d\n", brp_2
);
1400 if (brp_2
>= aarch64
->brp_num
) {
1401 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1405 breakpoint
->set
= brp_1
+ 1;
1406 breakpoint
->linked_BRP
= brp_2
;
1407 control_CTX
= ((CTX_machmode
& 0x7) << 20)
1410 | (CTX_byte_addr_select
<< 5)
1412 brp_list
[brp_1
].used
= 1;
1413 brp_list
[brp_1
].value
= (breakpoint
->asid
);
1414 brp_list
[brp_1
].control
= control_CTX
;
1415 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1416 + CPUDBG_BVR_BASE
+ 4 * brp_list
[brp_1
].BRPn
,
1417 brp_list
[brp_1
].value
);
1418 if (retval
!= ERROR_OK
)
1420 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1421 + CPUDBG_BCR_BASE
+ 4 * brp_list
[brp_1
].BRPn
,
1422 brp_list
[brp_1
].control
);
1423 if (retval
!= ERROR_OK
)
1426 control_IVA
= ((IVA_machmode
& 0x7) << 20)
1428 | (IVA_byte_addr_select
<< 5)
1430 brp_list
[brp_2
].used
= 1;
1431 brp_list
[brp_2
].value
= (breakpoint
->address
& 0xFFFFFFFC);
1432 brp_list
[brp_2
].control
= control_IVA
;
1433 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1434 + CPUDBG_BVR_BASE
+ 4 * brp_list
[brp_2
].BRPn
,
1435 brp_list
[brp_2
].value
);
1436 if (retval
!= ERROR_OK
)
1438 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1439 + CPUDBG_BCR_BASE
+ 4 * brp_list
[brp_2
].BRPn
,
1440 brp_list
[brp_2
].control
);
1441 if (retval
!= ERROR_OK
)
1447 static int aarch64_unset_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1450 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1451 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1452 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1454 if (!breakpoint
->set
) {
1455 LOG_WARNING("breakpoint not set");
1459 if (breakpoint
->type
== BKPT_HARD
) {
1460 if ((breakpoint
->address
!= 0) && (breakpoint
->asid
!= 0)) {
1461 int brp_i
= breakpoint
->set
- 1;
1462 int brp_j
= breakpoint
->linked_BRP
;
1463 if ((brp_i
< 0) || (brp_i
>= aarch64
->brp_num
)) {
1464 LOG_DEBUG("Invalid BRP number in breakpoint");
1467 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1468 brp_list
[brp_i
].control
, brp_list
[brp_i
].value
);
1469 brp_list
[brp_i
].used
= 0;
1470 brp_list
[brp_i
].value
= 0;
1471 brp_list
[brp_i
].control
= 0;
1472 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1473 + CPUDBG_BCR_BASE
+ 16 * brp_list
[brp_i
].BRPn
,
1474 brp_list
[brp_i
].control
);
1475 if (retval
!= ERROR_OK
)
1477 if ((brp_j
< 0) || (brp_j
>= aarch64
->brp_num
)) {
1478 LOG_DEBUG("Invalid BRP number in breakpoint");
1481 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%0" PRIx64
, brp_j
,
1482 brp_list
[brp_j
].control
, brp_list
[brp_j
].value
);
1483 brp_list
[brp_j
].used
= 0;
1484 brp_list
[brp_j
].value
= 0;
1485 brp_list
[brp_j
].control
= 0;
1486 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1487 + CPUDBG_BCR_BASE
+ 16 * brp_list
[brp_j
].BRPn
,
1488 brp_list
[brp_j
].control
);
1489 if (retval
!= ERROR_OK
)
1491 breakpoint
->linked_BRP
= 0;
1492 breakpoint
->set
= 0;
1496 int brp_i
= breakpoint
->set
- 1;
1497 if ((brp_i
< 0) || (brp_i
>= aarch64
->brp_num
)) {
1498 LOG_DEBUG("Invalid BRP number in breakpoint");
1501 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%0" PRIx64
, brp_i
,
1502 brp_list
[brp_i
].control
, brp_list
[brp_i
].value
);
1503 brp_list
[brp_i
].used
= 0;
1504 brp_list
[brp_i
].value
= 0;
1505 brp_list
[brp_i
].control
= 0;
1506 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1507 + CPUDBG_BCR_BASE
+ 4 * brp_list
[brp_i
].BRPn
,
1508 brp_list
[brp_i
].control
);
1509 if (retval
!= ERROR_OK
)
1511 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1512 + CPUDBG_BVR_BASE
+ 4 * brp_list
[brp_i
].BRPn
,
1513 brp_list
[brp_i
].value
);
1514 if (retval
!= ERROR_OK
)
1516 breakpoint
->set
= 0;
1520 /* restore original instruction (kept in target endianness) */
1521 if (breakpoint
->length
== 4) {
1522 retval
= target_write_memory(target
,
1523 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1524 4, 1, breakpoint
->orig_instr
);
1525 if (retval
!= ERROR_OK
)
1528 retval
= target_write_memory(target
,
1529 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1530 2, 1, breakpoint
->orig_instr
);
1531 if (retval
!= ERROR_OK
)
1535 breakpoint
->set
= 0;
1540 static int aarch64_add_breakpoint(struct target
*target
,
1541 struct breakpoint
*breakpoint
)
1543 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1545 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1546 LOG_INFO("no hardware breakpoint available");
1547 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1550 if (breakpoint
->type
== BKPT_HARD
)
1551 aarch64
->brp_num_available
--;
1553 return aarch64_set_breakpoint(target
, breakpoint
, 0x00); /* Exact match */
1556 static int aarch64_add_context_breakpoint(struct target
*target
,
1557 struct breakpoint
*breakpoint
)
1559 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1561 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1562 LOG_INFO("no hardware breakpoint available");
1563 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1566 if (breakpoint
->type
== BKPT_HARD
)
1567 aarch64
->brp_num_available
--;
1569 return aarch64_set_context_breakpoint(target
, breakpoint
, 0x02); /* asid match */
1572 static int aarch64_add_hybrid_breakpoint(struct target
*target
,
1573 struct breakpoint
*breakpoint
)
1575 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1577 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1578 LOG_INFO("no hardware breakpoint available");
1579 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1582 if (breakpoint
->type
== BKPT_HARD
)
1583 aarch64
->brp_num_available
--;
1585 return aarch64_set_hybrid_breakpoint(target
, breakpoint
); /* ??? */
1589 static int aarch64_remove_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1591 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1594 /* It is perfectly possible to remove breakpoints while the target is running */
1595 if (target
->state
!= TARGET_HALTED
) {
1596 LOG_WARNING("target not halted");
1597 return ERROR_TARGET_NOT_HALTED
;
1601 if (breakpoint
->set
) {
1602 aarch64_unset_breakpoint(target
, breakpoint
);
1603 if (breakpoint
->type
== BKPT_HARD
)
1604 aarch64
->brp_num_available
++;
1611 * Cortex-A8 Reset functions
1614 static int aarch64_assert_reset(struct target
*target
)
1616 struct armv8_common
*armv8
= target_to_armv8(target
);
1620 /* FIXME when halt is requested, make it work somehow... */
1622 /* Issue some kind of warm reset. */
1623 if (target_has_event_action(target
, TARGET_EVENT_RESET_ASSERT
))
1624 target_handle_event(target
, TARGET_EVENT_RESET_ASSERT
);
1625 else if (jtag_get_reset_config() & RESET_HAS_SRST
) {
1626 /* REVISIT handle "pulls" cases, if there's
1627 * hardware that needs them to work.
1629 jtag_add_reset(0, 1);
1631 LOG_ERROR("%s: how to reset?", target_name(target
));
1635 /* registers are now invalid */
1636 register_cache_invalidate(armv8
->arm
.core_cache
);
1638 target
->state
= TARGET_RESET
;
1643 static int aarch64_deassert_reset(struct target
*target
)
1649 /* be certain SRST is off */
1650 jtag_add_reset(0, 0);
1652 retval
= aarch64_poll(target
);
1653 if (retval
!= ERROR_OK
)
1656 if (target
->reset_halt
) {
1657 if (target
->state
!= TARGET_HALTED
) {
1658 LOG_WARNING("%s: ran after reset and before halt ...",
1659 target_name(target
));
1660 retval
= target_halt(target
);
1661 if (retval
!= ERROR_OK
)
1669 static int aarch64_write_apb_ab_memory(struct target
*target
,
1670 uint64_t address
, uint32_t size
,
1671 uint32_t count
, const uint8_t *buffer
)
1673 /* write memory through APB-AP */
1674 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
1675 struct armv8_common
*armv8
= target_to_armv8(target
);
1676 struct arm
*arm
= &armv8
->arm
;
1677 int total_bytes
= count
* size
;
1679 int start_byte
= address
& 0x3;
1680 int end_byte
= (address
+ total_bytes
) & 0x3;
1683 uint8_t *tmp_buff
= NULL
;
1686 LOG_DEBUG("Writing APB-AP memory address 0x%" PRIx64
" size %" PRIu32
" count%" PRIu32
,
1687 address
, size
, count
);
1688 if (target
->state
!= TARGET_HALTED
) {
1689 LOG_WARNING("target not halted");
1690 return ERROR_TARGET_NOT_HALTED
;
1693 total_u32
= DIV_ROUND_UP((address
& 3) + total_bytes
, 4);
1695 /* Mark register R0 as dirty, as it will be used
1696 * for transferring the data.
1697 * It will be restored automatically when exiting
1700 reg
= armv8_reg_current(arm
, 1);
1703 reg
= armv8_reg_current(arm
, 0);
1706 /* clear any abort */
1707 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
, armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1708 if (retval
!= ERROR_OK
)
1711 /* This algorithm comes from either :
1712 * Cortex-A8 TRM Example 12-25
1713 * Cortex-R4 TRM Example 11-26
1714 * (slight differences)
1717 /* The algorithm only copies 32 bit words, so the buffer
1718 * should be expanded to include the words at either end.
1719 * The first and last words will be read first to avoid
1720 * corruption if needed.
1722 tmp_buff
= malloc(total_u32
* 4);
1724 if ((start_byte
!= 0) && (total_u32
> 1)) {
1725 /* First bytes not aligned - read the 32 bit word to avoid corrupting
1726 * the other bytes in the word.
1728 retval
= aarch64_read_apb_ab_memory(target
, (address
& ~0x3), 4, 1, tmp_buff
);
1729 if (retval
!= ERROR_OK
)
1730 goto error_free_buff_w
;
1733 /* If end of write is not aligned, or the write is less than 4 bytes */
1734 if ((end_byte
!= 0) ||
1735 ((total_u32
== 1) && (total_bytes
!= 4))) {
1737 /* Read the last word to avoid corruption during 32 bit write */
1738 int mem_offset
= (total_u32
-1) * 4;
1739 retval
= aarch64_read_apb_ab_memory(target
, (address
& ~0x3) + mem_offset
, 4, 1, &tmp_buff
[mem_offset
]);
1740 if (retval
!= ERROR_OK
)
1741 goto error_free_buff_w
;
1744 /* Copy the write buffer over the top of the temporary buffer */
1745 memcpy(&tmp_buff
[start_byte
], buffer
, total_bytes
);
1747 /* We now have a 32 bit aligned buffer that can be written */
1750 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1751 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1752 if (retval
!= ERROR_OK
)
1753 goto error_free_buff_w
;
1755 /* Set DTR mode to Normal*/
1756 dscr
= (dscr
& ~DSCR_EXT_DCC_MASK
) | DSCR_EXT_DCC_NON_BLOCKING
;
1757 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1758 armv8
->debug_base
+ CPUDBG_DSCR
, dscr
);
1759 if (retval
!= ERROR_OK
)
1760 goto error_free_buff_w
;
1763 LOG_WARNING("reading size >4 bytes not yet supported");
1764 goto error_unset_dtr_w
;
1767 retval
= aarch64_instr_write_data_dcc_64(arm
->dpm
, 0xd5330401, address
+4);
1768 if (retval
!= ERROR_OK
)
1769 goto error_unset_dtr_w
;
1771 dscr
= DSCR_INSTR_COMP
;
1772 while (i
< count
* size
) {
1775 memcpy(&val
, &buffer
[i
], size
);
1776 retval
= aarch64_instr_write_data_dcc(arm
->dpm
, 0xd5330500, val
);
1777 if (retval
!= ERROR_OK
)
1778 goto error_unset_dtr_w
;
1780 retval
= aarch64_exec_opcode(target
, 0xb81fc020, &dscr
);
1781 if (retval
!= ERROR_OK
)
1782 goto error_unset_dtr_w
;
1784 retval
= aarch64_exec_opcode(target
, 0x91001021, &dscr
);
1785 if (retval
!= ERROR_OK
)
1786 goto error_unset_dtr_w
;
1791 /* Check for sticky abort flags in the DSCR */
1792 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1793 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1794 if (retval
!= ERROR_OK
)
1795 goto error_free_buff_w
;
1796 if (dscr
& (DSCR_STICKY_ABORT_PRECISE
| DSCR_STICKY_ABORT_IMPRECISE
)) {
1797 /* Abort occurred - clear it and exit */
1798 LOG_ERROR("abort occurred - dscr = 0x%08" PRIx32
, dscr
);
1799 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1800 armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1801 goto error_free_buff_w
;
1809 /* Unset DTR mode */
1810 mem_ap_read_atomic_u32(armv8
->debug_ap
,
1811 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1812 dscr
= (dscr
& ~DSCR_EXT_DCC_MASK
) | DSCR_EXT_DCC_NON_BLOCKING
;
1813 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1814 armv8
->debug_base
+ CPUDBG_DSCR
, dscr
);
1821 static int aarch64_read_apb_ab_memory(struct target
*target
,
1822 target_addr_t address
, uint32_t size
,
1823 uint32_t count
, uint8_t *buffer
)
1825 /* read memory through APB-AP */
1827 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
1828 struct armv8_common
*armv8
= target_to_armv8(target
);
1829 struct arm
*arm
= &armv8
->arm
;
1832 uint8_t *tmp_buff
= NULL
;
1835 LOG_DEBUG("Reading APB-AP memory address 0x%" TARGET_PRIxADDR
" size %" PRIu32
" count%" PRIu32
,
1836 address
, size
, count
);
1837 if (target
->state
!= TARGET_HALTED
) {
1838 LOG_WARNING("target not halted");
1839 return ERROR_TARGET_NOT_HALTED
;
1842 /* Mark register R0 as dirty, as it will be used
1843 * for transferring the data.
1844 * It will be restored automatically when exiting
1847 reg
= armv8_reg_current(arm
, 0);
1850 /* clear any abort */
1851 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1852 armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1853 if (retval
!= ERROR_OK
)
1854 goto error_free_buff_r
;
1856 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1857 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1858 if (retval
!= ERROR_OK
)
1859 goto error_unset_dtr_r
;
1862 LOG_WARNING("reading size >4 bytes not yet supported");
1863 goto error_unset_dtr_r
;
1866 while (i
< count
* size
) {
1868 retval
= aarch64_instr_write_data_dcc_64(arm
->dpm
, 0xd5330400, address
+4);
1869 if (retval
!= ERROR_OK
)
1870 goto error_unset_dtr_r
;
1871 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1872 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1874 dscr
= DSCR_INSTR_COMP
;
1875 retval
= aarch64_exec_opcode(target
, 0xb85fc000, &dscr
);
1876 if (retval
!= ERROR_OK
)
1877 goto error_unset_dtr_r
;
1878 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1879 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
1881 retval
= aarch64_instr_read_data_dcc(arm
->dpm
, 0xd5130400, &val
);
1882 if (retval
!= ERROR_OK
)
1883 goto error_unset_dtr_r
;
1884 memcpy(&buffer
[i
], &val
, size
);
1889 /* Clear any sticky error */
1890 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1891 armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1897 LOG_WARNING("DSCR = 0x%" PRIx32
, dscr
);
1898 /* Todo: Unset DTR mode */
1904 /* Clear any sticky error */
1905 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1906 armv8
->debug_base
+ CPUDBG_DRCR
, 1<<2);
1911 static int aarch64_read_phys_memory(struct target
*target
,
1912 target_addr_t address
, uint32_t size
,
1913 uint32_t count
, uint8_t *buffer
)
1915 struct armv8_common
*armv8
= target_to_armv8(target
);
1916 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
1917 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
1918 uint8_t apsel
= swjdp
->apsel
;
1919 LOG_DEBUG("Reading memory at real address 0x%" TARGET_PRIxADDR
"; size %" PRId32
"; count %" PRId32
,
1920 address
, size
, count
);
1922 if (count
&& buffer
) {
1924 if (armv8
->memory_ap_available
&& (apsel
== armv8
->memory_ap
->ap_num
)) {
1926 /* read memory through AHB-AP */
1927 retval
= mem_ap_read_buf(armv8
->memory_ap
, buffer
, size
, count
, address
);
1929 /* read memory through APB-AP */
1930 retval
= aarch64_mmu_modify(target
, 0);
1931 if (retval
!= ERROR_OK
)
1933 retval
= aarch64_read_apb_ab_memory(target
, address
, size
, count
, buffer
);
1939 static int aarch64_read_memory(struct target
*target
, target_addr_t address
,
1940 uint32_t size
, uint32_t count
, uint8_t *buffer
)
1942 int mmu_enabled
= 0;
1943 target_addr_t virt
, phys
;
1945 struct armv8_common
*armv8
= target_to_armv8(target
);
1946 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
1947 uint8_t apsel
= swjdp
->apsel
;
1949 /* aarch64 handles unaligned memory access */
1950 LOG_DEBUG("Reading memory at address 0x%" TARGET_PRIxADDR
"; size %" PRId32
"; count %" PRId32
, address
,
1953 /* determine if MMU was enabled on target stop */
1954 if (!armv8
->is_armv7r
) {
1955 retval
= aarch64_mmu(target
, &mmu_enabled
);
1956 if (retval
!= ERROR_OK
)
1960 if (armv8
->memory_ap_available
&& (apsel
== armv8
->memory_ap
->ap_num
)) {
1963 retval
= aarch64_virt2phys(target
, virt
, &phys
);
1964 if (retval
!= ERROR_OK
)
1967 LOG_DEBUG("Reading at virtual address. Translating v:0x%" TARGET_PRIxADDR
" to r:0x%" TARGET_PRIxADDR
,
1971 retval
= aarch64_read_phys_memory(target
, address
, size
, count
,
1975 retval
= aarch64_check_address(target
, address
);
1976 if (retval
!= ERROR_OK
)
1978 /* enable MMU as we could have disabled it for phys
1980 retval
= aarch64_mmu_modify(target
, 1);
1981 if (retval
!= ERROR_OK
)
1984 retval
= aarch64_read_apb_ab_memory(target
, address
, size
,
1990 static int aarch64_write_phys_memory(struct target
*target
,
1991 target_addr_t address
, uint32_t size
,
1992 uint32_t count
, const uint8_t *buffer
)
1994 struct armv8_common
*armv8
= target_to_armv8(target
);
1995 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
1996 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
1997 uint8_t apsel
= swjdp
->apsel
;
1999 LOG_DEBUG("Writing memory to real address 0x%" TARGET_PRIxADDR
"; size %" PRId32
"; count %" PRId32
, address
,
2002 if (count
&& buffer
) {
2004 if (armv8
->memory_ap_available
&& (apsel
== armv8
->memory_ap
->ap_num
)) {
2006 /* write memory through AHB-AP */
2007 retval
= mem_ap_write_buf(armv8
->memory_ap
, buffer
, size
, count
, address
);
2010 /* write memory through APB-AP */
2011 if (!armv8
->is_armv7r
) {
2012 retval
= aarch64_mmu_modify(target
, 0);
2013 if (retval
!= ERROR_OK
)
2016 return aarch64_write_apb_ab_memory(target
, address
, size
, count
, buffer
);
2021 /* REVISIT this op is generic ARMv7-A/R stuff */
2022 if (retval
== ERROR_OK
&& target
->state
== TARGET_HALTED
) {
2023 struct arm_dpm
*dpm
= armv8
->arm
.dpm
;
2025 retval
= dpm
->prepare(dpm
);
2026 if (retval
!= ERROR_OK
)
2029 /* The Cache handling will NOT work with MMU active, the
2030 * wrong addresses will be invalidated!
2032 * For both ICache and DCache, walk all cache lines in the
2033 * address range. Cortex-A8 has fixed 64 byte line length.
2035 * REVISIT per ARMv7, these may trigger watchpoints ...
2038 /* invalidate I-Cache */
2039 if (armv8
->armv8_mmu
.armv8_cache
.i_cache_enabled
) {
2040 /* ICIMVAU - Invalidate Cache single entry
2042 * MCR p15, 0, r0, c7, c5, 1
2044 for (uint32_t cacheline
= address
;
2045 cacheline
< address
+ size
* count
;
2047 retval
= dpm
->instr_write_data_r0(dpm
,
2048 ARMV4_5_MCR(15, 0, 0, 7, 5, 1),
2050 if (retval
!= ERROR_OK
)
2055 /* invalidate D-Cache */
2056 if (armv8
->armv8_mmu
.armv8_cache
.d_u_cache_enabled
) {
2057 /* DCIMVAC - Invalidate data Cache line
2059 * MCR p15, 0, r0, c7, c6, 1
2061 for (uint32_t cacheline
= address
;
2062 cacheline
< address
+ size
* count
;
2064 retval
= dpm
->instr_write_data_r0(dpm
,
2065 ARMV4_5_MCR(15, 0, 0, 7, 6, 1),
2067 if (retval
!= ERROR_OK
)
2072 /* (void) */ dpm
->finish(dpm
);
2078 static int aarch64_write_memory(struct target
*target
, target_addr_t address
,
2079 uint32_t size
, uint32_t count
, const uint8_t *buffer
)
2081 int mmu_enabled
= 0;
2082 target_addr_t virt
, phys
;
2084 struct armv8_common
*armv8
= target_to_armv8(target
);
2085 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
2086 uint8_t apsel
= swjdp
->apsel
;
2088 /* aarch64 handles unaligned memory access */
2089 LOG_DEBUG("Writing memory at address 0x%" TARGET_PRIxADDR
"; size %" PRId32
2090 "; count %" PRId32
, address
, size
, count
);
2092 /* determine if MMU was enabled on target stop */
2093 if (!armv8
->is_armv7r
) {
2094 retval
= aarch64_mmu(target
, &mmu_enabled
);
2095 if (retval
!= ERROR_OK
)
2099 if (armv8
->memory_ap_available
&& (apsel
== armv8
->memory_ap
->ap_num
)) {
2100 LOG_DEBUG("Writing memory to address 0x%" TARGET_PRIxADDR
"; size %"
2101 PRId32
"; count %" PRId32
, address
, size
, count
);
2104 retval
= aarch64_virt2phys(target
, virt
, &phys
);
2105 if (retval
!= ERROR_OK
)
2108 LOG_DEBUG("Writing to virtual address. Translating v:0x%"
2109 TARGET_PRIxADDR
" to r:0x%" TARGET_PRIxADDR
, virt
, phys
);
2112 retval
= aarch64_write_phys_memory(target
, address
, size
,
2116 retval
= aarch64_check_address(target
, address
);
2117 if (retval
!= ERROR_OK
)
2119 /* enable MMU as we could have disabled it for phys access */
2120 retval
= aarch64_mmu_modify(target
, 1);
2121 if (retval
!= ERROR_OK
)
2124 retval
= aarch64_write_apb_ab_memory(target
, address
, size
, count
, buffer
);
2129 static int aarch64_handle_target_request(void *priv
)
2131 struct target
*target
= priv
;
2132 struct armv8_common
*armv8
= target_to_armv8(target
);
2135 if (!target_was_examined(target
))
2137 if (!target
->dbg_msg_enabled
)
2140 if (target
->state
== TARGET_RUNNING
) {
2143 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2144 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
2146 /* check if we have data */
2147 while ((dscr
& DSCR_DTR_TX_FULL
) && (retval
== ERROR_OK
)) {
2148 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2149 armv8
->debug_base
+ CPUDBG_DTRTX
, &request
);
2150 if (retval
== ERROR_OK
) {
2151 target_request(target
, request
);
2152 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2153 armv8
->debug_base
+ CPUDBG_DSCR
, &dscr
);
2161 static int aarch64_examine_first(struct target
*target
)
2163 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
2164 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
2165 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
2166 int retval
= ERROR_OK
;
2167 uint32_t pfr
, debug
, ctypr
, ttypr
, cpuid
;
2170 /* We do one extra read to ensure DAP is configured,
2171 * we call ahbap_debugport_init(swjdp) instead
2173 retval
= dap_dp_init(swjdp
);
2174 if (retval
!= ERROR_OK
)
2177 /* Search for the APB-AB - it is needed for access to debug registers */
2178 retval
= dap_find_ap(swjdp
, AP_TYPE_APB_AP
, &armv8
->debug_ap
);
2179 if (retval
!= ERROR_OK
) {
2180 LOG_ERROR("Could not find APB-AP for debug access");
2184 retval
= mem_ap_init(armv8
->debug_ap
);
2185 if (retval
!= ERROR_OK
) {
2186 LOG_ERROR("Could not initialize the APB-AP");
2190 armv8
->debug_ap
->memaccess_tck
= 80;
2192 /* Search for the AHB-AB */
2193 armv8
->memory_ap_available
= false;
2194 retval
= dap_find_ap(swjdp
, AP_TYPE_AHB_AP
, &armv8
->memory_ap
);
2195 if (retval
== ERROR_OK
) {
2196 retval
= mem_ap_init(armv8
->memory_ap
);
2197 if (retval
== ERROR_OK
)
2198 armv8
->memory_ap_available
= true;
2200 if (retval
!= ERROR_OK
) {
2201 /* AHB-AP not found or unavailable - use the CPU */
2202 LOG_DEBUG("No AHB-AP available for memory access");
2206 if (!target
->dbgbase_set
) {
2208 /* Get ROM Table base */
2210 int32_t coreidx
= target
->coreid
;
2211 retval
= dap_get_debugbase(armv8
->debug_ap
, &dbgbase
, &apid
);
2212 if (retval
!= ERROR_OK
)
2214 /* Lookup 0x15 -- Processor DAP */
2215 retval
= dap_lookup_cs_component(armv8
->debug_ap
, dbgbase
, 0x15,
2216 &armv8
->debug_base
, &coreidx
);
2217 if (retval
!= ERROR_OK
)
2219 LOG_DEBUG("Detected core %" PRId32
" dbgbase: %08" PRIx32
,
2220 coreidx
, armv8
->debug_base
);
2222 armv8
->debug_base
= target
->dbgbase
;
2224 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2225 armv8
->debug_base
+ 0x300, 0);
2226 if (retval
!= ERROR_OK
) {
2227 LOG_DEBUG("Examine %s failed", "oslock");
2231 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2232 armv8
->debug_base
+ 0x88, &cpuid
);
2233 LOG_DEBUG("0x88 = %x", cpuid
);
2235 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2236 armv8
->debug_base
+ 0x314, &cpuid
);
2237 LOG_DEBUG("0x314 = %x", cpuid
);
2239 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2240 armv8
->debug_base
+ 0x310, &cpuid
);
2241 LOG_DEBUG("0x310 = %x", cpuid
);
2242 if (retval
!= ERROR_OK
)
2245 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2246 armv8
->debug_base
+ CPUDBG_CPUID
, &cpuid
);
2247 if (retval
!= ERROR_OK
) {
2248 LOG_DEBUG("Examine %s failed", "CPUID");
2252 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2253 armv8
->debug_base
+ CPUDBG_CTYPR
, &ctypr
);
2254 if (retval
!= ERROR_OK
) {
2255 LOG_DEBUG("Examine %s failed", "CTYPR");
2259 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2260 armv8
->debug_base
+ CPUDBG_TTYPR
, &ttypr
);
2261 if (retval
!= ERROR_OK
) {
2262 LOG_DEBUG("Examine %s failed", "TTYPR");
2266 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2267 armv8
->debug_base
+ ID_AA64PFR0_EL1
, &pfr
);
2268 if (retval
!= ERROR_OK
) {
2269 LOG_DEBUG("Examine %s failed", "ID_AA64DFR0_EL1");
2272 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2273 armv8
->debug_base
+ ID_AA64DFR0_EL1
, &debug
);
2274 if (retval
!= ERROR_OK
) {
2275 LOG_DEBUG("Examine %s failed", "ID_AA64DFR0_EL1");
2279 LOG_DEBUG("cpuid = 0x%08" PRIx32
, cpuid
);
2280 LOG_DEBUG("ctypr = 0x%08" PRIx32
, ctypr
);
2281 LOG_DEBUG("ttypr = 0x%08" PRIx32
, ttypr
);
2282 LOG_DEBUG("ID_AA64PFR0_EL1 = 0x%08" PRIx32
, pfr
);
2283 LOG_DEBUG("ID_AA64DFR0_EL1 = 0x%08" PRIx32
, debug
);
2285 armv8
->arm
.core_type
= ARM_MODE_MON
;
2286 armv8
->arm
.core_state
= ARM_STATE_AARCH64
;
2287 retval
= aarch64_dpm_setup(aarch64
, debug
);
2288 if (retval
!= ERROR_OK
)
2291 /* Setup Breakpoint Register Pairs */
2292 aarch64
->brp_num
= ((debug
>> 12) & 0x0F) + 1;
2293 aarch64
->brp_num_context
= ((debug
>> 28) & 0x0F) + 1;
2295 /* hack - no context bpt support yet */
2296 aarch64
->brp_num_context
= 0;
2298 aarch64
->brp_num_available
= aarch64
->brp_num
;
2299 aarch64
->brp_list
= calloc(aarch64
->brp_num
, sizeof(struct aarch64_brp
));
2300 for (i
= 0; i
< aarch64
->brp_num
; i
++) {
2301 aarch64
->brp_list
[i
].used
= 0;
2302 if (i
< (aarch64
->brp_num
-aarch64
->brp_num_context
))
2303 aarch64
->brp_list
[i
].type
= BRP_NORMAL
;
2305 aarch64
->brp_list
[i
].type
= BRP_CONTEXT
;
2306 aarch64
->brp_list
[i
].value
= 0;
2307 aarch64
->brp_list
[i
].control
= 0;
2308 aarch64
->brp_list
[i
].BRPn
= i
;
2311 LOG_DEBUG("Configured %i hw breakpoints", aarch64
->brp_num
);
2313 target_set_examined(target
);
2317 static int aarch64_examine(struct target
*target
)
2319 int retval
= ERROR_OK
;
2321 /* don't re-probe hardware after each reset */
2322 if (!target_was_examined(target
))
2323 retval
= aarch64_examine_first(target
);
2325 /* Configure core debug access */
2326 if (retval
== ERROR_OK
)
2327 retval
= aarch64_init_debug_access(target
);
2333 * Cortex-A8 target creation and initialization
2336 static int aarch64_init_target(struct command_context
*cmd_ctx
,
2337 struct target
*target
)
2339 /* examine_first() does a bunch of this */
2343 static int aarch64_init_arch_info(struct target
*target
,
2344 struct aarch64_common
*aarch64
, struct jtag_tap
*tap
)
2346 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
2347 struct adiv5_dap
*dap
= armv8
->arm
.dap
;
2349 armv8
->arm
.dap
= dap
;
2351 /* Setup struct aarch64_common */
2352 aarch64
->common_magic
= AARCH64_COMMON_MAGIC
;
2353 /* tap has no dap initialized */
2355 tap
->dap
= dap_init();
2357 /* Leave (only) generic DAP stuff for debugport_init() */
2358 tap
->dap
->tap
= tap
;
2361 armv8
->arm
.dap
= tap
->dap
;
2363 aarch64
->fast_reg_read
= 0;
2365 /* register arch-specific functions */
2366 armv8
->examine_debug_reason
= NULL
;
2368 armv8
->post_debug_entry
= aarch64_post_debug_entry
;
2370 armv8
->pre_restore_context
= NULL
;
2372 armv8
->armv8_mmu
.read_physical_memory
= aarch64_read_phys_memory
;
2374 /* REVISIT v7a setup should be in a v7a-specific routine */
2375 armv8_init_arch_info(target
, armv8
);
2376 target_register_timer_callback(aarch64_handle_target_request
, 1, 1, target
);
2381 static int aarch64_target_create(struct target
*target
, Jim_Interp
*interp
)
2383 struct aarch64_common
*aarch64
= calloc(1, sizeof(struct aarch64_common
));
2385 aarch64
->armv8_common
.is_armv7r
= false;
2387 return aarch64_init_arch_info(target
, aarch64
, target
->tap
);
2390 static int aarch64_mmu(struct target
*target
, int *enabled
)
2392 if (target
->state
!= TARGET_HALTED
) {
2393 LOG_ERROR("%s: target not halted", __func__
);
2394 return ERROR_TARGET_INVALID
;
2397 *enabled
= target_to_aarch64(target
)->armv8_common
.armv8_mmu
.mmu_enabled
;
2401 static int aarch64_virt2phys(struct target
*target
, target_addr_t virt
,
2402 target_addr_t
*phys
)
2404 int retval
= ERROR_FAIL
;
2405 struct armv8_common
*armv8
= target_to_armv8(target
);
2406 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
2407 uint8_t apsel
= swjdp
->apsel
;
2408 if (armv8
->memory_ap_available
&& (apsel
== armv8
->memory_ap
->ap_num
)) {
2410 retval
= armv8_mmu_translate_va(target
,
2412 if (retval
!= ERROR_OK
)
2415 } else {/* use this method if armv8->memory_ap not selected
2416 * mmu must be enable in order to get a correct translation */
2417 retval
= aarch64_mmu_modify(target
, 1);
2418 if (retval
!= ERROR_OK
)
2420 retval
= armv8_mmu_translate_va_pa(target
, virt
, phys
, 1);
2426 COMMAND_HANDLER(aarch64_handle_cache_info_command
)
2428 struct target
*target
= get_current_target(CMD_CTX
);
2429 struct armv8_common
*armv8
= target_to_armv8(target
);
2431 return armv8_handle_cache_info_command(CMD_CTX
,
2432 &armv8
->armv8_mmu
.armv8_cache
);
2436 COMMAND_HANDLER(aarch64_handle_dbginit_command
)
2438 struct target
*target
= get_current_target(CMD_CTX
);
2439 if (!target_was_examined(target
)) {
2440 LOG_ERROR("target not examined yet");
2444 return aarch64_init_debug_access(target
);
2446 COMMAND_HANDLER(aarch64_handle_smp_off_command
)
2448 struct target
*target
= get_current_target(CMD_CTX
);
2449 /* check target is an smp target */
2450 struct target_list
*head
;
2451 struct target
*curr
;
2452 head
= target
->head
;
2454 if (head
!= (struct target_list
*)NULL
) {
2455 while (head
!= (struct target_list
*)NULL
) {
2456 curr
= head
->target
;
2460 /* fixes the target display to the debugger */
2461 target
->gdb_service
->target
= target
;
2466 COMMAND_HANDLER(aarch64_handle_smp_on_command
)
2468 struct target
*target
= get_current_target(CMD_CTX
);
2469 struct target_list
*head
;
2470 struct target
*curr
;
2471 head
= target
->head
;
2472 if (head
!= (struct target_list
*)NULL
) {
2474 while (head
!= (struct target_list
*)NULL
) {
2475 curr
= head
->target
;
2483 COMMAND_HANDLER(aarch64_handle_smp_gdb_command
)
2485 struct target
*target
= get_current_target(CMD_CTX
);
2486 int retval
= ERROR_OK
;
2487 struct target_list
*head
;
2488 head
= target
->head
;
2489 if (head
!= (struct target_list
*)NULL
) {
2490 if (CMD_ARGC
== 1) {
2492 COMMAND_PARSE_NUMBER(int, CMD_ARGV
[0], coreid
);
2493 if (ERROR_OK
!= retval
)
2495 target
->gdb_service
->core
[1] = coreid
;
2498 command_print(CMD_CTX
, "gdb coreid %" PRId32
" -> %" PRId32
, target
->gdb_service
->core
[0]
2499 , target
->gdb_service
->core
[1]);
2504 static const struct command_registration aarch64_exec_command_handlers
[] = {
2506 .name
= "cache_info",
2507 .handler
= aarch64_handle_cache_info_command
,
2508 .mode
= COMMAND_EXEC
,
2509 .help
= "display information about target caches",
2514 .handler
= aarch64_handle_dbginit_command
,
2515 .mode
= COMMAND_EXEC
,
2516 .help
= "Initialize core debug",
2519 { .name
= "smp_off",
2520 .handler
= aarch64_handle_smp_off_command
,
2521 .mode
= COMMAND_EXEC
,
2522 .help
= "Stop smp handling",
2527 .handler
= aarch64_handle_smp_on_command
,
2528 .mode
= COMMAND_EXEC
,
2529 .help
= "Restart smp handling",
2534 .handler
= aarch64_handle_smp_gdb_command
,
2535 .mode
= COMMAND_EXEC
,
2536 .help
= "display/fix current core played to gdb",
2541 COMMAND_REGISTRATION_DONE
2543 static const struct command_registration aarch64_command_handlers
[] = {
2545 .chain
= arm_command_handlers
,
2548 .chain
= armv8_command_handlers
,
2552 .mode
= COMMAND_ANY
,
2553 .help
= "Cortex-A command group",
2555 .chain
= aarch64_exec_command_handlers
,
2557 COMMAND_REGISTRATION_DONE
2560 struct target_type aarch64_target
= {
2563 .poll
= aarch64_poll
,
2564 .arch_state
= armv8_arch_state
,
2566 .halt
= aarch64_halt
,
2567 .resume
= aarch64_resume
,
2568 .step
= aarch64_step
,
2570 .assert_reset
= aarch64_assert_reset
,
2571 .deassert_reset
= aarch64_deassert_reset
,
2573 /* REVISIT allow exporting VFP3 registers ... */
2574 .get_gdb_reg_list
= armv8_get_gdb_reg_list
,
2576 .read_memory
= aarch64_read_memory
,
2577 .write_memory
= aarch64_write_memory
,
2579 .checksum_memory
= arm_checksum_memory
,
2580 .blank_check_memory
= arm_blank_check_memory
,
2582 .run_algorithm
= armv4_5_run_algorithm
,
2584 .add_breakpoint
= aarch64_add_breakpoint
,
2585 .add_context_breakpoint
= aarch64_add_context_breakpoint
,
2586 .add_hybrid_breakpoint
= aarch64_add_hybrid_breakpoint
,
2587 .remove_breakpoint
= aarch64_remove_breakpoint
,
2588 .add_watchpoint
= NULL
,
2589 .remove_watchpoint
= NULL
,
2591 .commands
= aarch64_command_handlers
,
2592 .target_create
= aarch64_target_create
,
2593 .init_target
= aarch64_init_target
,
2594 .examine
= aarch64_examine
,
2596 .read_phys_memory
= aarch64_read_phys_memory
,
2597 .write_phys_memory
= aarch64_write_phys_memory
,
2599 .virt2phys
= aarch64_virt2phys
,
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)