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"
26 #include "a64_disassembler.h"
28 #include "target_request.h"
29 #include "target_type.h"
30 #include "armv8_opcodes.h"
31 #include "armv8_cache.h"
32 #include "arm_coresight.h"
33 #include "arm_semihosting.h"
34 #include "jtag/interface.h"
36 #include <helper/time_support.h>
48 struct aarch64_private_config
{
49 struct adiv5_private_config adiv5_config
;
53 static int aarch64_poll(struct target
*target
);
54 static int aarch64_debug_entry(struct target
*target
);
55 static int aarch64_restore_context(struct target
*target
, bool bpwp
);
56 static int aarch64_set_breakpoint(struct target
*target
,
57 struct breakpoint
*breakpoint
, uint8_t matchmode
);
58 static int aarch64_set_context_breakpoint(struct target
*target
,
59 struct breakpoint
*breakpoint
, uint8_t matchmode
);
60 static int aarch64_set_hybrid_breakpoint(struct target
*target
,
61 struct breakpoint
*breakpoint
);
62 static int aarch64_unset_breakpoint(struct target
*target
,
63 struct breakpoint
*breakpoint
);
64 static int aarch64_mmu(struct target
*target
, int *enabled
);
65 static int aarch64_virt2phys(struct target
*target
,
66 target_addr_t virt
, target_addr_t
*phys
);
67 static int aarch64_read_cpu_memory(struct target
*target
,
68 uint64_t address
, uint32_t size
, uint32_t count
, uint8_t *buffer
);
70 static int aarch64_restore_system_control_reg(struct target
*target
)
72 enum arm_mode target_mode
= ARM_MODE_ANY
;
73 int retval
= ERROR_OK
;
76 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
77 struct armv8_common
*armv8
= target_to_armv8(target
);
79 if (aarch64
->system_control_reg
!= aarch64
->system_control_reg_curr
) {
80 aarch64
->system_control_reg_curr
= aarch64
->system_control_reg
;
81 /* LOG_INFO("cp15_control_reg: %8.8" PRIx32, cortex_v8->cp15_control_reg); */
83 switch (armv8
->arm
.core_mode
) {
85 target_mode
= ARMV8_64_EL1H
;
89 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL1
, 0);
93 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL2
, 0);
97 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL3
, 0);
107 instr
= ARMV4_5_MCR(15, 0, 0, 1, 0, 0);
111 LOG_ERROR("cannot read system control register in this mode: (%s : 0x%x)",
112 armv8_mode_name(armv8
->arm
.core_mode
), armv8
->arm
.core_mode
);
116 if (target_mode
!= ARM_MODE_ANY
)
117 armv8_dpm_modeswitch(&armv8
->dpm
, target_mode
);
119 retval
= armv8
->dpm
.instr_write_data_r0(&armv8
->dpm
, instr
, aarch64
->system_control_reg
);
120 if (retval
!= ERROR_OK
)
123 if (target_mode
!= ARM_MODE_ANY
)
124 armv8_dpm_modeswitch(&armv8
->dpm
, ARM_MODE_ANY
);
130 /* modify system_control_reg in order to enable or disable mmu for :
131 * - virt2phys address conversion
132 * - read or write memory in phys or virt address */
133 static int aarch64_mmu_modify(struct target
*target
, int enable
)
135 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
136 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
137 int retval
= ERROR_OK
;
138 enum arm_mode target_mode
= ARM_MODE_ANY
;
142 /* if mmu enabled at target stop and mmu not enable */
143 if (!(aarch64
->system_control_reg
& 0x1U
)) {
144 LOG_ERROR("trying to enable mmu on target stopped with mmu disable");
147 if (!(aarch64
->system_control_reg_curr
& 0x1U
))
148 aarch64
->system_control_reg_curr
|= 0x1U
;
150 if (aarch64
->system_control_reg_curr
& 0x4U
) {
151 /* data cache is active */
152 aarch64
->system_control_reg_curr
&= ~0x4U
;
153 /* flush data cache armv8 function to be called */
154 if (armv8
->armv8_mmu
.armv8_cache
.flush_all_data_cache
)
155 armv8
->armv8_mmu
.armv8_cache
.flush_all_data_cache(target
);
157 if ((aarch64
->system_control_reg_curr
& 0x1U
)) {
158 aarch64
->system_control_reg_curr
&= ~0x1U
;
162 switch (armv8
->arm
.core_mode
) {
164 target_mode
= ARMV8_64_EL1H
;
168 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL1
, 0);
172 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL2
, 0);
176 instr
= ARMV8_MSR_GP(SYSTEM_SCTLR_EL3
, 0);
186 instr
= ARMV4_5_MCR(15, 0, 0, 1, 0, 0);
190 LOG_DEBUG("unknown cpu state 0x%x", armv8
->arm
.core_mode
);
193 if (target_mode
!= ARM_MODE_ANY
)
194 armv8_dpm_modeswitch(&armv8
->dpm
, target_mode
);
196 retval
= armv8
->dpm
.instr_write_data_r0(&armv8
->dpm
, instr
,
197 aarch64
->system_control_reg_curr
);
199 if (target_mode
!= ARM_MODE_ANY
)
200 armv8_dpm_modeswitch(&armv8
->dpm
, ARM_MODE_ANY
);
206 * Basic debug access, very low level assumes state is saved
208 static int aarch64_init_debug_access(struct target
*target
)
210 struct armv8_common
*armv8
= target_to_armv8(target
);
214 LOG_DEBUG("%s", target_name(target
));
216 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
217 armv8
->debug_base
+ CPUV8_DBG_OSLAR
, 0);
218 if (retval
!= ERROR_OK
) {
219 LOG_DEBUG("Examine %s failed", "oslock");
223 /* Clear Sticky Power Down status Bit in PRSR to enable access to
224 the registers in the Core Power Domain */
225 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
226 armv8
->debug_base
+ CPUV8_DBG_PRSR
, &dummy
);
227 if (retval
!= ERROR_OK
)
231 * Static CTI configuration:
232 * Channel 0 -> trigger outputs HALT request to PE
233 * Channel 1 -> trigger outputs Resume request to PE
234 * Gate all channel trigger events from entering the CTM
238 retval
= arm_cti_enable(armv8
->cti
, true);
239 /* By default, gate all channel events to and from the CTM */
240 if (retval
== ERROR_OK
)
241 retval
= arm_cti_write_reg(armv8
->cti
, CTI_GATE
, 0);
242 /* output halt requests to PE on channel 0 event */
243 if (retval
== ERROR_OK
)
244 retval
= arm_cti_write_reg(armv8
->cti
, CTI_OUTEN0
, CTI_CHNL(0));
245 /* output restart requests to PE on channel 1 event */
246 if (retval
== ERROR_OK
)
247 retval
= arm_cti_write_reg(armv8
->cti
, CTI_OUTEN1
, CTI_CHNL(1));
248 if (retval
!= ERROR_OK
)
251 /* Resync breakpoint registers */
256 /* Write to memory mapped registers directly with no cache or mmu handling */
257 static int aarch64_dap_write_memap_register_u32(struct target
*target
,
258 target_addr_t address
,
262 struct armv8_common
*armv8
= target_to_armv8(target
);
264 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
, address
, value
);
269 static int aarch64_dpm_setup(struct aarch64_common
*a8
, uint64_t debug
)
271 struct arm_dpm
*dpm
= &a8
->armv8_common
.dpm
;
274 dpm
->arm
= &a8
->armv8_common
.arm
;
277 retval
= armv8_dpm_setup(dpm
);
278 if (retval
== ERROR_OK
)
279 retval
= armv8_dpm_initialize(dpm
);
284 static int aarch64_set_dscr_bits(struct target
*target
, unsigned long bit_mask
, unsigned long value
)
286 struct armv8_common
*armv8
= target_to_armv8(target
);
287 return armv8_set_dbgreg_bits(armv8
, CPUV8_DBG_DSCR
, bit_mask
, value
);
290 static int aarch64_check_state_one(struct target
*target
,
291 uint32_t mask
, uint32_t val
, int *p_result
, uint32_t *p_prsr
)
293 struct armv8_common
*armv8
= target_to_armv8(target
);
297 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
298 armv8
->debug_base
+ CPUV8_DBG_PRSR
, &prsr
);
299 if (retval
!= ERROR_OK
)
306 *p_result
= (prsr
& mask
) == (val
& mask
);
311 static int aarch64_wait_halt_one(struct target
*target
)
313 int retval
= ERROR_OK
;
316 int64_t then
= timeval_ms();
320 retval
= aarch64_check_state_one(target
, PRSR_HALT
, PRSR_HALT
, &halted
, &prsr
);
321 if (retval
!= ERROR_OK
|| halted
)
324 if (timeval_ms() > then
+ 1000) {
325 retval
= ERROR_TARGET_TIMEOUT
;
326 LOG_DEBUG("target %s timeout, prsr=0x%08"PRIx32
, target_name(target
), prsr
);
333 static int aarch64_prepare_halt_smp(struct target
*target
, bool exc_target
, struct target
**p_first
)
335 int retval
= ERROR_OK
;
336 struct target_list
*head
;
337 struct target
*first
= NULL
;
339 LOG_DEBUG("target %s exc %i", target_name(target
), exc_target
);
341 foreach_smp_target(head
, target
->smp_targets
) {
342 struct target
*curr
= head
->target
;
343 struct armv8_common
*armv8
= target_to_armv8(curr
);
345 if (exc_target
&& curr
== target
)
347 if (!target_was_examined(curr
))
349 if (curr
->state
!= TARGET_RUNNING
)
352 /* HACK: mark this target as prepared for halting */
353 curr
->debug_reason
= DBG_REASON_DBGRQ
;
355 /* open the gate for channel 0 to let HALT requests pass to the CTM */
356 retval
= arm_cti_ungate_channel(armv8
->cti
, 0);
357 if (retval
== ERROR_OK
)
358 retval
= aarch64_set_dscr_bits(curr
, DSCR_HDE
, DSCR_HDE
);
359 if (retval
!= ERROR_OK
)
362 LOG_DEBUG("target %s prepared", target_name(curr
));
369 if (exc_target
&& first
)
378 static int aarch64_halt_one(struct target
*target
, enum halt_mode mode
)
380 int retval
= ERROR_OK
;
381 struct armv8_common
*armv8
= target_to_armv8(target
);
383 LOG_DEBUG("%s", target_name(target
));
385 /* allow Halting Debug Mode */
386 retval
= aarch64_set_dscr_bits(target
, DSCR_HDE
, DSCR_HDE
);
387 if (retval
!= ERROR_OK
)
390 /* trigger an event on channel 0, this outputs a halt request to the PE */
391 retval
= arm_cti_pulse_channel(armv8
->cti
, 0);
392 if (retval
!= ERROR_OK
)
395 if (mode
== HALT_SYNC
) {
396 retval
= aarch64_wait_halt_one(target
);
397 if (retval
!= ERROR_OK
) {
398 if (retval
== ERROR_TARGET_TIMEOUT
)
399 LOG_ERROR("Timeout waiting for target %s halt", target_name(target
));
407 static int aarch64_halt_smp(struct target
*target
, bool exc_target
)
409 struct target
*next
= target
;
412 /* prepare halt on all PEs of the group */
413 retval
= aarch64_prepare_halt_smp(target
, exc_target
, &next
);
415 if (exc_target
&& next
== target
)
418 /* halt the target PE */
419 if (retval
== ERROR_OK
)
420 retval
= aarch64_halt_one(next
, HALT_LAZY
);
422 if (retval
!= ERROR_OK
)
425 /* wait for all PEs to halt */
426 int64_t then
= timeval_ms();
428 bool all_halted
= true;
429 struct target_list
*head
;
432 foreach_smp_target(head
, target
->smp_targets
) {
437 if (!target_was_examined(curr
))
440 retval
= aarch64_check_state_one(curr
, PRSR_HALT
, PRSR_HALT
, &halted
, NULL
);
441 if (retval
!= ERROR_OK
|| !halted
) {
450 if (timeval_ms() > then
+ 1000) {
451 retval
= ERROR_TARGET_TIMEOUT
;
456 * HACK: on Hi6220 there are 8 cores organized in 2 clusters
457 * and it looks like the CTI's are not connected by a common
458 * trigger matrix. It seems that we need to halt one core in each
459 * cluster explicitly. So if we find that a core has not halted
460 * yet, we trigger an explicit halt for the second cluster.
462 retval
= aarch64_halt_one(curr
, HALT_LAZY
);
463 if (retval
!= ERROR_OK
)
470 static int update_halt_gdb(struct target
*target
, enum target_debug_reason debug_reason
)
472 struct target
*gdb_target
= NULL
;
473 struct target_list
*head
;
476 if (debug_reason
== DBG_REASON_NOTHALTED
) {
477 LOG_DEBUG("Halting remaining targets in SMP group");
478 aarch64_halt_smp(target
, true);
481 /* poll all targets in the group, but skip the target that serves GDB */
482 foreach_smp_target(head
, target
->smp_targets
) {
484 /* skip calling context */
487 if (!target_was_examined(curr
))
489 /* skip targets that were already halted */
490 if (curr
->state
== TARGET_HALTED
)
492 /* remember the gdb_service->target */
493 if (curr
->gdb_service
)
494 gdb_target
= curr
->gdb_service
->target
;
496 if (curr
== gdb_target
)
499 /* avoid recursion in aarch64_poll() */
505 /* after all targets were updated, poll the gdb serving target */
506 if (gdb_target
&& gdb_target
!= target
)
507 aarch64_poll(gdb_target
);
513 * Aarch64 Run control
516 static int aarch64_poll(struct target
*target
)
518 enum target_state prev_target_state
;
519 int retval
= ERROR_OK
;
522 retval
= aarch64_check_state_one(target
,
523 PRSR_HALT
, PRSR_HALT
, &halted
, NULL
);
524 if (retval
!= ERROR_OK
)
528 prev_target_state
= target
->state
;
529 if (prev_target_state
!= TARGET_HALTED
) {
530 enum target_debug_reason debug_reason
= target
->debug_reason
;
532 /* We have a halting debug event */
533 target
->state
= TARGET_HALTED
;
534 LOG_DEBUG("Target %s halted", target_name(target
));
535 retval
= aarch64_debug_entry(target
);
536 if (retval
!= ERROR_OK
)
540 update_halt_gdb(target
, debug_reason
);
542 if (arm_semihosting(target
, &retval
) != 0)
545 switch (prev_target_state
) {
549 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
551 case TARGET_DEBUG_RUNNING
:
552 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_HALTED
);
559 target
->state
= TARGET_RUNNING
;
564 static int aarch64_halt(struct target
*target
)
566 struct armv8_common
*armv8
= target_to_armv8(target
);
567 armv8
->last_run_control_op
= ARMV8_RUNCONTROL_HALT
;
570 return aarch64_halt_smp(target
, false);
572 return aarch64_halt_one(target
, HALT_SYNC
);
575 static int aarch64_restore_one(struct target
*target
, int current
,
576 uint64_t *address
, int handle_breakpoints
, int debug_execution
)
578 struct armv8_common
*armv8
= target_to_armv8(target
);
579 struct arm
*arm
= &armv8
->arm
;
583 LOG_DEBUG("%s", target_name(target
));
585 if (!debug_execution
)
586 target_free_all_working_areas(target
);
588 /* current = 1: continue on current pc, otherwise continue at <address> */
589 resume_pc
= buf_get_u64(arm
->pc
->value
, 0, 64);
591 resume_pc
= *address
;
593 *address
= resume_pc
;
595 /* Make sure that the Armv7 gdb thumb fixups does not
596 * kill the return address
598 switch (arm
->core_state
) {
600 resume_pc
&= 0xFFFFFFFC;
602 case ARM_STATE_AARCH64
:
603 resume_pc
&= 0xFFFFFFFFFFFFFFFC;
605 case ARM_STATE_THUMB
:
606 case ARM_STATE_THUMB_EE
:
607 /* When the return address is loaded into PC
608 * bit 0 must be 1 to stay in Thumb state
612 case ARM_STATE_JAZELLE
:
613 LOG_ERROR("How do I resume into Jazelle state??");
616 LOG_DEBUG("resume pc = 0x%016" PRIx64
, resume_pc
);
617 buf_set_u64(arm
->pc
->value
, 0, 64, resume_pc
);
618 arm
->pc
->dirty
= true;
619 arm
->pc
->valid
= true;
621 /* called it now before restoring context because it uses cpu
622 * register r0 for restoring system control register */
623 retval
= aarch64_restore_system_control_reg(target
);
624 if (retval
== ERROR_OK
)
625 retval
= aarch64_restore_context(target
, handle_breakpoints
);
631 * prepare single target for restart
635 static int aarch64_prepare_restart_one(struct target
*target
)
637 struct armv8_common
*armv8
= target_to_armv8(target
);
642 LOG_DEBUG("%s", target_name(target
));
644 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
645 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
646 if (retval
!= ERROR_OK
)
649 if ((dscr
& DSCR_ITE
) == 0)
650 LOG_ERROR("DSCR.ITE must be set before leaving debug!");
651 if ((dscr
& DSCR_ERR
) != 0)
652 LOG_ERROR("DSCR.ERR must be cleared before leaving debug!");
654 /* acknowledge a pending CTI halt event */
655 retval
= arm_cti_ack_events(armv8
->cti
, CTI_TRIG(HALT
));
657 * open the CTI gate for channel 1 so that the restart events
658 * get passed along to all PEs. Also close gate for channel 0
659 * to isolate the PE from halt events.
661 if (retval
== ERROR_OK
)
662 retval
= arm_cti_ungate_channel(armv8
->cti
, 1);
663 if (retval
== ERROR_OK
)
664 retval
= arm_cti_gate_channel(armv8
->cti
, 0);
666 /* make sure that DSCR.HDE is set */
667 if (retval
== ERROR_OK
) {
669 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
670 armv8
->debug_base
+ CPUV8_DBG_DSCR
, dscr
);
673 if (retval
== ERROR_OK
) {
674 /* clear sticky bits in PRSR, SDR is now 0 */
675 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
676 armv8
->debug_base
+ CPUV8_DBG_PRSR
, &tmp
);
682 static int aarch64_do_restart_one(struct target
*target
, enum restart_mode mode
)
684 struct armv8_common
*armv8
= target_to_armv8(target
);
687 LOG_DEBUG("%s", target_name(target
));
689 /* trigger an event on channel 1, generates a restart request to the PE */
690 retval
= arm_cti_pulse_channel(armv8
->cti
, 1);
691 if (retval
!= ERROR_OK
)
694 if (mode
== RESTART_SYNC
) {
695 int64_t then
= timeval_ms();
699 * if PRSR.SDR is set now, the target did restart, even
700 * if it's now already halted again (e.g. due to breakpoint)
702 retval
= aarch64_check_state_one(target
,
703 PRSR_SDR
, PRSR_SDR
, &resumed
, NULL
);
704 if (retval
!= ERROR_OK
|| resumed
)
707 if (timeval_ms() > then
+ 1000) {
708 LOG_ERROR("%s: Timeout waiting for resume"PRIx32
, target_name(target
));
709 retval
= ERROR_TARGET_TIMEOUT
;
715 if (retval
!= ERROR_OK
)
718 target
->debug_reason
= DBG_REASON_NOTHALTED
;
719 target
->state
= TARGET_RUNNING
;
724 static int aarch64_restart_one(struct target
*target
, enum restart_mode mode
)
728 LOG_DEBUG("%s", target_name(target
));
730 retval
= aarch64_prepare_restart_one(target
);
731 if (retval
== ERROR_OK
)
732 retval
= aarch64_do_restart_one(target
, mode
);
738 * prepare all but the current target for restart
740 static int aarch64_prep_restart_smp(struct target
*target
, int handle_breakpoints
, struct target
**p_first
)
742 int retval
= ERROR_OK
;
743 struct target_list
*head
;
744 struct target
*first
= NULL
;
747 foreach_smp_target(head
, target
->smp_targets
) {
748 struct target
*curr
= head
->target
;
750 /* skip calling target */
753 if (!target_was_examined(curr
))
755 if (curr
->state
!= TARGET_HALTED
)
758 /* resume at current address, not in step mode */
759 retval
= aarch64_restore_one(curr
, 1, &address
, handle_breakpoints
, 0);
760 if (retval
== ERROR_OK
)
761 retval
= aarch64_prepare_restart_one(curr
);
762 if (retval
!= ERROR_OK
) {
763 LOG_ERROR("failed to restore target %s", target_name(curr
));
766 /* remember the first valid target in the group */
778 static int aarch64_step_restart_smp(struct target
*target
)
780 int retval
= ERROR_OK
;
781 struct target_list
*head
;
782 struct target
*first
= NULL
;
784 LOG_DEBUG("%s", target_name(target
));
786 retval
= aarch64_prep_restart_smp(target
, 0, &first
);
787 if (retval
!= ERROR_OK
)
791 retval
= aarch64_do_restart_one(first
, RESTART_LAZY
);
792 if (retval
!= ERROR_OK
) {
793 LOG_DEBUG("error restarting target %s", target_name(first
));
797 int64_t then
= timeval_ms();
799 struct target
*curr
= target
;
800 bool all_resumed
= true;
802 foreach_smp_target(head
, target
->smp_targets
) {
811 if (!target_was_examined(curr
))
814 retval
= aarch64_check_state_one(curr
,
815 PRSR_SDR
, PRSR_SDR
, &resumed
, &prsr
);
816 if (retval
!= ERROR_OK
|| (!resumed
&& (prsr
& PRSR_HALT
))) {
821 if (curr
->state
!= TARGET_RUNNING
) {
822 curr
->state
= TARGET_RUNNING
;
823 curr
->debug_reason
= DBG_REASON_NOTHALTED
;
824 target_call_event_callbacks(curr
, TARGET_EVENT_RESUMED
);
831 if (timeval_ms() > then
+ 1000) {
832 LOG_ERROR("%s: timeout waiting for target resume", __func__
);
833 retval
= ERROR_TARGET_TIMEOUT
;
837 * HACK: on Hi6220 there are 8 cores organized in 2 clusters
838 * and it looks like the CTI's are not connected by a common
839 * trigger matrix. It seems that we need to halt one core in each
840 * cluster explicitly. So if we find that a core has not halted
841 * yet, we trigger an explicit resume for the second cluster.
843 retval
= aarch64_do_restart_one(curr
, RESTART_LAZY
);
844 if (retval
!= ERROR_OK
)
851 static int aarch64_resume(struct target
*target
, int current
,
852 target_addr_t address
, int handle_breakpoints
, int debug_execution
)
855 uint64_t addr
= address
;
857 struct armv8_common
*armv8
= target_to_armv8(target
);
858 armv8
->last_run_control_op
= ARMV8_RUNCONTROL_RESUME
;
860 if (target
->state
!= TARGET_HALTED
)
861 return ERROR_TARGET_NOT_HALTED
;
864 * If this target is part of a SMP group, prepare the others
865 * targets for resuming. This involves restoring the complete
866 * target register context and setting up CTI gates to accept
867 * resume events from the trigger matrix.
870 retval
= aarch64_prep_restart_smp(target
, handle_breakpoints
, NULL
);
871 if (retval
!= ERROR_OK
)
875 /* all targets prepared, restore and restart the current target */
876 retval
= aarch64_restore_one(target
, current
, &addr
, handle_breakpoints
,
878 if (retval
== ERROR_OK
)
879 retval
= aarch64_restart_one(target
, RESTART_SYNC
);
880 if (retval
!= ERROR_OK
)
884 int64_t then
= timeval_ms();
886 struct target
*curr
= target
;
887 struct target_list
*head
;
888 bool all_resumed
= true;
890 foreach_smp_target(head
, target
->smp_targets
) {
897 if (!target_was_examined(curr
))
900 retval
= aarch64_check_state_one(curr
,
901 PRSR_SDR
, PRSR_SDR
, &resumed
, &prsr
);
902 if (retval
!= ERROR_OK
|| (!resumed
&& (prsr
& PRSR_HALT
))) {
907 if (curr
->state
!= TARGET_RUNNING
) {
908 curr
->state
= TARGET_RUNNING
;
909 curr
->debug_reason
= DBG_REASON_NOTHALTED
;
910 target_call_event_callbacks(curr
, TARGET_EVENT_RESUMED
);
917 if (timeval_ms() > then
+ 1000) {
918 LOG_ERROR("%s: timeout waiting for target %s to resume", __func__
, target_name(curr
));
919 retval
= ERROR_TARGET_TIMEOUT
;
924 * HACK: on Hi6220 there are 8 cores organized in 2 clusters
925 * and it looks like the CTI's are not connected by a common
926 * trigger matrix. It seems that we need to halt one core in each
927 * cluster explicitly. So if we find that a core has not halted
928 * yet, we trigger an explicit resume for the second cluster.
930 retval
= aarch64_do_restart_one(curr
, RESTART_LAZY
);
931 if (retval
!= ERROR_OK
)
936 if (retval
!= ERROR_OK
)
939 target
->debug_reason
= DBG_REASON_NOTHALTED
;
941 if (!debug_execution
) {
942 target
->state
= TARGET_RUNNING
;
943 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
944 LOG_DEBUG("target resumed at 0x%" PRIx64
, addr
);
946 target
->state
= TARGET_DEBUG_RUNNING
;
947 target_call_event_callbacks(target
, TARGET_EVENT_DEBUG_RESUMED
);
948 LOG_DEBUG("target debug resumed at 0x%" PRIx64
, addr
);
954 static int aarch64_debug_entry(struct target
*target
)
956 int retval
= ERROR_OK
;
957 struct armv8_common
*armv8
= target_to_armv8(target
);
958 struct arm_dpm
*dpm
= &armv8
->dpm
;
959 enum arm_state core_state
;
962 /* make sure to clear all sticky errors */
963 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
964 armv8
->debug_base
+ CPUV8_DBG_DRCR
, DRCR_CSE
);
965 if (retval
== ERROR_OK
)
966 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
967 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
968 if (retval
== ERROR_OK
)
969 retval
= arm_cti_ack_events(armv8
->cti
, CTI_TRIG(HALT
));
971 if (retval
!= ERROR_OK
)
974 LOG_DEBUG("%s dscr = 0x%08" PRIx32
, target_name(target
), dscr
);
977 core_state
= armv8_dpm_get_core_state(dpm
);
978 armv8_select_opcodes(armv8
, core_state
== ARM_STATE_AARCH64
);
979 armv8_select_reg_access(armv8
, core_state
== ARM_STATE_AARCH64
);
981 /* close the CTI gate for all events */
982 if (retval
== ERROR_OK
)
983 retval
= arm_cti_write_reg(armv8
->cti
, CTI_GATE
, 0);
984 /* discard async exceptions */
985 if (retval
== ERROR_OK
)
986 retval
= dpm
->instr_cpsr_sync(dpm
);
987 if (retval
!= ERROR_OK
)
990 /* Examine debug reason */
991 armv8_dpm_report_dscr(dpm
, dscr
);
993 /* save the memory address that triggered the watchpoint */
994 if (target
->debug_reason
== DBG_REASON_WATCHPOINT
) {
997 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
998 armv8
->debug_base
+ CPUV8_DBG_EDWAR0
, &tmp
);
999 if (retval
!= ERROR_OK
)
1001 target_addr_t edwar
= tmp
;
1003 /* EDWAR[63:32] has unknown content in aarch32 state */
1004 if (core_state
== ARM_STATE_AARCH64
) {
1005 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1006 armv8
->debug_base
+ CPUV8_DBG_EDWAR1
, &tmp
);
1007 if (retval
!= ERROR_OK
)
1009 edwar
|= ((target_addr_t
)tmp
) << 32;
1012 armv8
->dpm
.wp_addr
= edwar
;
1015 retval
= armv8_dpm_read_current_registers(&armv8
->dpm
);
1017 if (retval
== ERROR_OK
&& armv8
->post_debug_entry
)
1018 retval
= armv8
->post_debug_entry(target
);
1023 static int aarch64_post_debug_entry(struct target
*target
)
1025 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1026 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1028 enum arm_mode target_mode
= ARM_MODE_ANY
;
1031 switch (armv8
->arm
.core_mode
) {
1033 target_mode
= ARMV8_64_EL1H
;
1037 instr
= ARMV8_MRS(SYSTEM_SCTLR_EL1
, 0);
1041 instr
= ARMV8_MRS(SYSTEM_SCTLR_EL2
, 0);
1045 instr
= ARMV8_MRS(SYSTEM_SCTLR_EL3
, 0);
1055 instr
= ARMV4_5_MRC(15, 0, 0, 1, 0, 0);
1059 LOG_ERROR("cannot read system control register in this mode: (%s : 0x%x)",
1060 armv8_mode_name(armv8
->arm
.core_mode
), armv8
->arm
.core_mode
);
1064 if (target_mode
!= ARM_MODE_ANY
)
1065 armv8_dpm_modeswitch(&armv8
->dpm
, target_mode
);
1067 retval
= armv8
->dpm
.instr_read_data_r0(&armv8
->dpm
, instr
, &aarch64
->system_control_reg
);
1068 if (retval
!= ERROR_OK
)
1071 if (target_mode
!= ARM_MODE_ANY
)
1072 armv8_dpm_modeswitch(&armv8
->dpm
, ARM_MODE_ANY
);
1074 LOG_DEBUG("System_register: %8.8" PRIx32
, aarch64
->system_control_reg
);
1075 aarch64
->system_control_reg_curr
= aarch64
->system_control_reg
;
1077 if (armv8
->armv8_mmu
.armv8_cache
.info
== -1) {
1078 armv8_identify_cache(armv8
);
1079 armv8_read_mpidr(armv8
);
1082 armv8
->armv8_mmu
.mmu_enabled
=
1083 (aarch64
->system_control_reg
& 0x1U
) ? 1 : 0;
1084 armv8
->armv8_mmu
.armv8_cache
.d_u_cache_enabled
=
1085 (aarch64
->system_control_reg
& 0x4U
) ? 1 : 0;
1086 armv8
->armv8_mmu
.armv8_cache
.i_cache_enabled
=
1087 (aarch64
->system_control_reg
& 0x1000U
) ? 1 : 0;
1092 * single-step a target
1094 static int aarch64_step(struct target
*target
, int current
, target_addr_t address
,
1095 int handle_breakpoints
)
1097 struct armv8_common
*armv8
= target_to_armv8(target
);
1098 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1099 int saved_retval
= ERROR_OK
;
1103 armv8
->last_run_control_op
= ARMV8_RUNCONTROL_STEP
;
1105 if (target
->state
!= TARGET_HALTED
) {
1106 LOG_WARNING("target not halted");
1107 return ERROR_TARGET_NOT_HALTED
;
1110 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1111 armv8
->debug_base
+ CPUV8_DBG_EDECR
, &edecr
);
1112 /* make sure EDECR.SS is not set when restoring the register */
1114 if (retval
== ERROR_OK
) {
1116 /* set EDECR.SS to enter hardware step mode */
1117 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1118 armv8
->debug_base
+ CPUV8_DBG_EDECR
, (edecr
|0x4));
1120 /* disable interrupts while stepping */
1121 if (retval
== ERROR_OK
&& aarch64
->isrmasking_mode
== AARCH64_ISRMASK_ON
)
1122 retval
= aarch64_set_dscr_bits(target
, 0x3 << 22, 0x3 << 22);
1123 /* bail out if stepping setup has failed */
1124 if (retval
!= ERROR_OK
)
1127 if (target
->smp
&& (current
== 1)) {
1129 * isolate current target so that it doesn't get resumed
1130 * together with the others
1132 retval
= arm_cti_gate_channel(armv8
->cti
, 1);
1133 /* resume all other targets in the group */
1134 if (retval
== ERROR_OK
)
1135 retval
= aarch64_step_restart_smp(target
);
1136 if (retval
!= ERROR_OK
) {
1137 LOG_ERROR("Failed to restart non-stepping targets in SMP group");
1140 LOG_DEBUG("Restarted all non-stepping targets in SMP group");
1143 /* all other targets running, restore and restart the current target */
1144 retval
= aarch64_restore_one(target
, current
, &address
, 0, 0);
1145 if (retval
== ERROR_OK
)
1146 retval
= aarch64_restart_one(target
, RESTART_LAZY
);
1148 if (retval
!= ERROR_OK
)
1151 LOG_DEBUG("target step-resumed at 0x%" PRIx64
, address
);
1152 if (!handle_breakpoints
)
1153 target_call_event_callbacks(target
, TARGET_EVENT_RESUMED
);
1155 int64_t then
= timeval_ms();
1160 retval
= aarch64_check_state_one(target
,
1161 PRSR_SDR
|PRSR_HALT
, PRSR_SDR
|PRSR_HALT
, &stepped
, &prsr
);
1162 if (retval
!= ERROR_OK
|| stepped
)
1165 if (timeval_ms() > then
+ 100) {
1166 LOG_ERROR("timeout waiting for target %s halt after step",
1167 target_name(target
));
1168 retval
= ERROR_TARGET_TIMEOUT
;
1174 * At least on one SoC (Renesas R8A7795) stepping over a WFI instruction
1175 * causes a timeout. The core takes the step but doesn't complete it and so
1176 * debug state is never entered. However, you can manually halt the core
1177 * as an external debug even is also a WFI wakeup event.
1179 if (retval
== ERROR_TARGET_TIMEOUT
)
1180 saved_retval
= aarch64_halt_one(target
, HALT_SYNC
);
1183 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1184 armv8
->debug_base
+ CPUV8_DBG_EDECR
, edecr
);
1185 if (retval
!= ERROR_OK
)
1188 /* restore interrupts */
1189 if (aarch64
->isrmasking_mode
== AARCH64_ISRMASK_ON
) {
1190 retval
= aarch64_set_dscr_bits(target
, 0x3 << 22, 0);
1191 if (retval
!= ERROR_OK
)
1195 if (saved_retval
!= ERROR_OK
)
1196 return saved_retval
;
1201 static int aarch64_restore_context(struct target
*target
, bool bpwp
)
1203 struct armv8_common
*armv8
= target_to_armv8(target
);
1204 struct arm
*arm
= &armv8
->arm
;
1208 LOG_DEBUG("%s", target_name(target
));
1210 if (armv8
->pre_restore_context
)
1211 armv8
->pre_restore_context(target
);
1213 retval
= armv8_dpm_write_dirty_registers(&armv8
->dpm
, bpwp
);
1214 if (retval
== ERROR_OK
) {
1215 /* registers are now invalid */
1216 register_cache_invalidate(arm
->core_cache
);
1217 register_cache_invalidate(arm
->core_cache
->next
);
1224 * Cortex-A8 Breakpoint and watchpoint functions
1227 /* Setup hardware Breakpoint Register Pair */
1228 static int aarch64_set_breakpoint(struct target
*target
,
1229 struct breakpoint
*breakpoint
, uint8_t matchmode
)
1234 uint8_t byte_addr_select
= 0x0F;
1235 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1236 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1237 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1239 if (breakpoint
->is_set
) {
1240 LOG_WARNING("breakpoint already set");
1244 if (breakpoint
->type
== BKPT_HARD
) {
1246 while (brp_list
[brp_i
].used
&& (brp_i
< aarch64
->brp_num
))
1248 if (brp_i
>= aarch64
->brp_num
) {
1249 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1250 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1252 breakpoint_hw_set(breakpoint
, brp_i
);
1253 if (breakpoint
->length
== 2)
1254 byte_addr_select
= (3 << (breakpoint
->address
& 0x02));
1255 control
= ((matchmode
& 0x7) << 20)
1257 | (byte_addr_select
<< 5)
1259 brp_list
[brp_i
].used
= 1;
1260 brp_list
[brp_i
].value
= breakpoint
->address
& 0xFFFFFFFFFFFFFFFC;
1261 brp_list
[brp_i
].control
= control
;
1262 bpt_value
= brp_list
[brp_i
].value
;
1264 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1265 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1266 (uint32_t)(bpt_value
& 0xFFFFFFFF));
1267 if (retval
!= ERROR_OK
)
1269 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1270 + CPUV8_DBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_i
].brpn
,
1271 (uint32_t)(bpt_value
>> 32));
1272 if (retval
!= ERROR_OK
)
1275 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1276 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1277 brp_list
[brp_i
].control
);
1278 if (retval
!= ERROR_OK
)
1280 LOG_DEBUG("brp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1281 brp_list
[brp_i
].control
,
1282 brp_list
[brp_i
].value
);
1284 } else if (breakpoint
->type
== BKPT_SOFT
) {
1288 if (armv8_dpm_get_core_state(&armv8
->dpm
) == ARM_STATE_AARCH64
) {
1289 opcode
= ARMV8_HLT(11);
1291 if (breakpoint
->length
!= 4)
1292 LOG_ERROR("bug: breakpoint length should be 4 in AArch64 mode");
1295 * core_state is ARM_STATE_ARM
1296 * in that case the opcode depends on breakpoint length:
1297 * - if length == 4 => A32 opcode
1298 * - if length == 2 => T32 opcode
1299 * - if length == 3 => T32 opcode (refer to gdb doc : ARM-Breakpoint-Kinds)
1300 * in that case the length should be changed from 3 to 4 bytes
1302 opcode
= (breakpoint
->length
== 4) ? ARMV8_HLT_A1(11) :
1303 (uint32_t) (ARMV8_HLT_T1(11) | ARMV8_HLT_T1(11) << 16);
1305 if (breakpoint
->length
== 3)
1306 breakpoint
->length
= 4;
1309 buf_set_u32(code
, 0, 32, opcode
);
1311 retval
= target_read_memory(target
,
1312 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1313 breakpoint
->length
, 1,
1314 breakpoint
->orig_instr
);
1315 if (retval
!= ERROR_OK
)
1318 armv8_cache_d_inner_flush_virt(armv8
,
1319 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1320 breakpoint
->length
);
1322 retval
= target_write_memory(target
,
1323 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1324 breakpoint
->length
, 1, code
);
1325 if (retval
!= ERROR_OK
)
1328 armv8_cache_d_inner_flush_virt(armv8
,
1329 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1330 breakpoint
->length
);
1332 armv8_cache_i_inner_inval_virt(armv8
,
1333 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1334 breakpoint
->length
);
1336 breakpoint
->is_set
= true;
1339 /* Ensure that halting debug mode is enable */
1340 retval
= aarch64_set_dscr_bits(target
, DSCR_HDE
, DSCR_HDE
);
1341 if (retval
!= ERROR_OK
) {
1342 LOG_DEBUG("Failed to set DSCR.HDE");
1349 static int aarch64_set_context_breakpoint(struct target
*target
,
1350 struct breakpoint
*breakpoint
, uint8_t matchmode
)
1352 int retval
= ERROR_FAIL
;
1355 uint8_t byte_addr_select
= 0x0F;
1356 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1357 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1358 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1360 if (breakpoint
->is_set
) {
1361 LOG_WARNING("breakpoint already set");
1364 /*check available context BRPs*/
1365 while ((brp_list
[brp_i
].used
||
1366 (brp_list
[brp_i
].type
!= BRP_CONTEXT
)) && (brp_i
< aarch64
->brp_num
))
1369 if (brp_i
>= aarch64
->brp_num
) {
1370 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1374 breakpoint_hw_set(breakpoint
, brp_i
);
1375 control
= ((matchmode
& 0x7) << 20)
1377 | (byte_addr_select
<< 5)
1379 brp_list
[brp_i
].used
= 1;
1380 brp_list
[brp_i
].value
= (breakpoint
->asid
);
1381 brp_list
[brp_i
].control
= control
;
1382 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1383 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1384 brp_list
[brp_i
].value
);
1385 if (retval
!= ERROR_OK
)
1387 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1388 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1389 brp_list
[brp_i
].control
);
1390 if (retval
!= ERROR_OK
)
1392 LOG_DEBUG("brp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1393 brp_list
[brp_i
].control
,
1394 brp_list
[brp_i
].value
);
1399 static int aarch64_set_hybrid_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1401 int retval
= ERROR_FAIL
;
1402 int brp_1
= 0; /* holds the contextID pair */
1403 int brp_2
= 0; /* holds the IVA pair */
1404 uint32_t control_ctx
, control_iva
;
1405 uint8_t ctx_byte_addr_select
= 0x0F;
1406 uint8_t iva_byte_addr_select
= 0x0F;
1407 uint8_t ctx_machmode
= 0x03;
1408 uint8_t iva_machmode
= 0x01;
1409 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1410 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1411 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1413 if (breakpoint
->is_set
) {
1414 LOG_WARNING("breakpoint already set");
1417 /*check available context BRPs*/
1418 while ((brp_list
[brp_1
].used
||
1419 (brp_list
[brp_1
].type
!= BRP_CONTEXT
)) && (brp_1
< aarch64
->brp_num
))
1422 LOG_DEBUG("brp(CTX) found num: %d", brp_1
);
1423 if (brp_1
>= aarch64
->brp_num
) {
1424 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1428 while ((brp_list
[brp_2
].used
||
1429 (brp_list
[brp_2
].type
!= BRP_NORMAL
)) && (brp_2
< aarch64
->brp_num
))
1432 LOG_DEBUG("brp(IVA) found num: %d", brp_2
);
1433 if (brp_2
>= aarch64
->brp_num
) {
1434 LOG_ERROR("ERROR Can not find free Breakpoint Register Pair");
1438 breakpoint_hw_set(breakpoint
, brp_1
);
1439 breakpoint
->linked_brp
= brp_2
;
1440 control_ctx
= ((ctx_machmode
& 0x7) << 20)
1443 | (ctx_byte_addr_select
<< 5)
1445 brp_list
[brp_1
].used
= 1;
1446 brp_list
[brp_1
].value
= (breakpoint
->asid
);
1447 brp_list
[brp_1
].control
= control_ctx
;
1448 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1449 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_1
].brpn
,
1450 brp_list
[brp_1
].value
);
1451 if (retval
!= ERROR_OK
)
1453 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1454 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_1
].brpn
,
1455 brp_list
[brp_1
].control
);
1456 if (retval
!= ERROR_OK
)
1459 control_iva
= ((iva_machmode
& 0x7) << 20)
1462 | (iva_byte_addr_select
<< 5)
1464 brp_list
[brp_2
].used
= 1;
1465 brp_list
[brp_2
].value
= breakpoint
->address
& 0xFFFFFFFFFFFFFFFC;
1466 brp_list
[brp_2
].control
= control_iva
;
1467 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1468 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_2
].brpn
,
1469 brp_list
[brp_2
].value
& 0xFFFFFFFF);
1470 if (retval
!= ERROR_OK
)
1472 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1473 + CPUV8_DBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_2
].brpn
,
1474 brp_list
[brp_2
].value
>> 32);
1475 if (retval
!= ERROR_OK
)
1477 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1478 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_2
].brpn
,
1479 brp_list
[brp_2
].control
);
1480 if (retval
!= ERROR_OK
)
1486 static int aarch64_unset_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1489 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1490 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1491 struct aarch64_brp
*brp_list
= aarch64
->brp_list
;
1493 if (!breakpoint
->is_set
) {
1494 LOG_WARNING("breakpoint not set");
1498 if (breakpoint
->type
== BKPT_HARD
) {
1499 if ((breakpoint
->address
!= 0) && (breakpoint
->asid
!= 0)) {
1500 int brp_i
= breakpoint
->number
;
1501 int brp_j
= breakpoint
->linked_brp
;
1502 if (brp_i
>= aarch64
->brp_num
) {
1503 LOG_DEBUG("Invalid BRP number in breakpoint");
1506 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, brp_i
,
1507 brp_list
[brp_i
].control
, brp_list
[brp_i
].value
);
1508 brp_list
[brp_i
].used
= 0;
1509 brp_list
[brp_i
].value
= 0;
1510 brp_list
[brp_i
].control
= 0;
1511 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1512 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1513 brp_list
[brp_i
].control
);
1514 if (retval
!= ERROR_OK
)
1516 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1517 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1518 (uint32_t)brp_list
[brp_i
].value
);
1519 if (retval
!= ERROR_OK
)
1521 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1522 + CPUV8_DBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_i
].brpn
,
1523 (uint32_t)brp_list
[brp_i
].value
);
1524 if (retval
!= ERROR_OK
)
1526 if ((brp_j
< 0) || (brp_j
>= aarch64
->brp_num
)) {
1527 LOG_DEBUG("Invalid BRP number in breakpoint");
1530 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%0" PRIx64
, brp_j
,
1531 brp_list
[brp_j
].control
, brp_list
[brp_j
].value
);
1532 brp_list
[brp_j
].used
= 0;
1533 brp_list
[brp_j
].value
= 0;
1534 brp_list
[brp_j
].control
= 0;
1535 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1536 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_j
].brpn
,
1537 brp_list
[brp_j
].control
);
1538 if (retval
!= ERROR_OK
)
1540 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1541 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_j
].brpn
,
1542 (uint32_t)brp_list
[brp_j
].value
);
1543 if (retval
!= ERROR_OK
)
1545 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1546 + CPUV8_DBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_j
].brpn
,
1547 (uint32_t)brp_list
[brp_j
].value
);
1548 if (retval
!= ERROR_OK
)
1551 breakpoint
->linked_brp
= 0;
1552 breakpoint
->is_set
= false;
1556 int brp_i
= breakpoint
->number
;
1557 if (brp_i
>= aarch64
->brp_num
) {
1558 LOG_DEBUG("Invalid BRP number in breakpoint");
1561 LOG_DEBUG("rbp %i control 0x%0" PRIx32
" value 0x%0" PRIx64
, brp_i
,
1562 brp_list
[brp_i
].control
, brp_list
[brp_i
].value
);
1563 brp_list
[brp_i
].used
= 0;
1564 brp_list
[brp_i
].value
= 0;
1565 brp_list
[brp_i
].control
= 0;
1566 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1567 + CPUV8_DBG_BCR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1568 brp_list
[brp_i
].control
);
1569 if (retval
!= ERROR_OK
)
1571 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1572 + CPUV8_DBG_BVR_BASE
+ 16 * brp_list
[brp_i
].brpn
,
1573 brp_list
[brp_i
].value
);
1574 if (retval
!= ERROR_OK
)
1577 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1578 + CPUV8_DBG_BVR_BASE
+ 4 + 16 * brp_list
[brp_i
].brpn
,
1579 (uint32_t)brp_list
[brp_i
].value
);
1580 if (retval
!= ERROR_OK
)
1582 breakpoint
->is_set
= false;
1586 /* restore original instruction (kept in target endianness) */
1588 armv8_cache_d_inner_flush_virt(armv8
,
1589 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1590 breakpoint
->length
);
1592 if (breakpoint
->length
== 4) {
1593 retval
= target_write_memory(target
,
1594 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1595 4, 1, breakpoint
->orig_instr
);
1596 if (retval
!= ERROR_OK
)
1599 retval
= target_write_memory(target
,
1600 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1601 2, 1, breakpoint
->orig_instr
);
1602 if (retval
!= ERROR_OK
)
1606 armv8_cache_d_inner_flush_virt(armv8
,
1607 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1608 breakpoint
->length
);
1610 armv8_cache_i_inner_inval_virt(armv8
,
1611 breakpoint
->address
& 0xFFFFFFFFFFFFFFFE,
1612 breakpoint
->length
);
1614 breakpoint
->is_set
= false;
1619 static int aarch64_add_breakpoint(struct target
*target
,
1620 struct breakpoint
*breakpoint
)
1622 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1624 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1625 LOG_INFO("no hardware breakpoint available");
1626 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1629 if (breakpoint
->type
== BKPT_HARD
)
1630 aarch64
->brp_num_available
--;
1632 return aarch64_set_breakpoint(target
, breakpoint
, 0x00); /* Exact match */
1635 static int aarch64_add_context_breakpoint(struct target
*target
,
1636 struct breakpoint
*breakpoint
)
1638 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1640 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1641 LOG_INFO("no hardware breakpoint available");
1642 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1645 if (breakpoint
->type
== BKPT_HARD
)
1646 aarch64
->brp_num_available
--;
1648 return aarch64_set_context_breakpoint(target
, breakpoint
, 0x02); /* asid match */
1651 static int aarch64_add_hybrid_breakpoint(struct target
*target
,
1652 struct breakpoint
*breakpoint
)
1654 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1656 if ((breakpoint
->type
== BKPT_HARD
) && (aarch64
->brp_num_available
< 1)) {
1657 LOG_INFO("no hardware breakpoint available");
1658 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1661 if (breakpoint
->type
== BKPT_HARD
)
1662 aarch64
->brp_num_available
--;
1664 return aarch64_set_hybrid_breakpoint(target
, breakpoint
); /* ??? */
1667 static int aarch64_remove_breakpoint(struct target
*target
, struct breakpoint
*breakpoint
)
1669 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1672 /* It is perfectly possible to remove breakpoints while the target is running */
1673 if (target
->state
!= TARGET_HALTED
) {
1674 LOG_WARNING("target not halted");
1675 return ERROR_TARGET_NOT_HALTED
;
1679 if (breakpoint
->is_set
) {
1680 aarch64_unset_breakpoint(target
, breakpoint
);
1681 if (breakpoint
->type
== BKPT_HARD
)
1682 aarch64
->brp_num_available
++;
1688 /* Setup hardware Watchpoint Register Pair */
1689 static int aarch64_set_watchpoint(struct target
*target
,
1690 struct watchpoint
*watchpoint
)
1694 uint32_t control
, offset
, length
;
1695 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1696 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1697 struct aarch64_brp
*wp_list
= aarch64
->wp_list
;
1699 if (watchpoint
->is_set
) {
1700 LOG_WARNING("watchpoint already set");
1704 while (wp_list
[wp_i
].used
&& (wp_i
< aarch64
->wp_num
))
1706 if (wp_i
>= aarch64
->wp_num
) {
1707 LOG_ERROR("ERROR Can not find free Watchpoint Register Pair");
1708 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1711 control
= (1 << 0) /* enable */
1712 | (3 << 1) /* both user and privileged access */
1713 | (1 << 13); /* higher mode control */
1715 switch (watchpoint
->rw
) {
1727 /* Match up to 8 bytes. */
1728 offset
= watchpoint
->address
& 7;
1729 length
= watchpoint
->length
;
1730 if (offset
+ length
> sizeof(uint64_t)) {
1731 length
= sizeof(uint64_t) - offset
;
1732 LOG_WARNING("Adjust watchpoint match inside 8-byte boundary");
1734 for (; length
> 0; offset
++, length
--)
1735 control
|= (1 << offset
) << 5;
1737 wp_list
[wp_i
].value
= watchpoint
->address
& 0xFFFFFFFFFFFFFFF8ULL
;
1738 wp_list
[wp_i
].control
= control
;
1740 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1741 + CPUV8_DBG_WVR_BASE
+ 16 * wp_list
[wp_i
].brpn
,
1742 (uint32_t)(wp_list
[wp_i
].value
& 0xFFFFFFFF));
1743 if (retval
!= ERROR_OK
)
1745 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1746 + CPUV8_DBG_WVR_BASE
+ 4 + 16 * wp_list
[wp_i
].brpn
,
1747 (uint32_t)(wp_list
[wp_i
].value
>> 32));
1748 if (retval
!= ERROR_OK
)
1751 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1752 + CPUV8_DBG_WCR_BASE
+ 16 * wp_list
[wp_i
].brpn
,
1754 if (retval
!= ERROR_OK
)
1756 LOG_DEBUG("wp %i control 0x%0" PRIx32
" value 0x%" TARGET_PRIxADDR
, wp_i
,
1757 wp_list
[wp_i
].control
, wp_list
[wp_i
].value
);
1759 /* Ensure that halting debug mode is enable */
1760 retval
= aarch64_set_dscr_bits(target
, DSCR_HDE
, DSCR_HDE
);
1761 if (retval
!= ERROR_OK
) {
1762 LOG_DEBUG("Failed to set DSCR.HDE");
1766 wp_list
[wp_i
].used
= 1;
1767 watchpoint_set(watchpoint
, wp_i
);
1772 /* Clear hardware Watchpoint Register Pair */
1773 static int aarch64_unset_watchpoint(struct target
*target
,
1774 struct watchpoint
*watchpoint
)
1777 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1778 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
1779 struct aarch64_brp
*wp_list
= aarch64
->wp_list
;
1781 if (!watchpoint
->is_set
) {
1782 LOG_WARNING("watchpoint not set");
1786 int wp_i
= watchpoint
->number
;
1787 if (wp_i
>= aarch64
->wp_num
) {
1788 LOG_DEBUG("Invalid WP number in watchpoint");
1791 LOG_DEBUG("rwp %i control 0x%0" PRIx32
" value 0x%0" PRIx64
, wp_i
,
1792 wp_list
[wp_i
].control
, wp_list
[wp_i
].value
);
1793 wp_list
[wp_i
].used
= 0;
1794 wp_list
[wp_i
].value
= 0;
1795 wp_list
[wp_i
].control
= 0;
1796 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1797 + CPUV8_DBG_WCR_BASE
+ 16 * wp_list
[wp_i
].brpn
,
1798 wp_list
[wp_i
].control
);
1799 if (retval
!= ERROR_OK
)
1801 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1802 + CPUV8_DBG_WVR_BASE
+ 16 * wp_list
[wp_i
].brpn
,
1803 wp_list
[wp_i
].value
);
1804 if (retval
!= ERROR_OK
)
1807 retval
= aarch64_dap_write_memap_register_u32(target
, armv8
->debug_base
1808 + CPUV8_DBG_WVR_BASE
+ 4 + 16 * wp_list
[wp_i
].brpn
,
1809 (uint32_t)wp_list
[wp_i
].value
);
1810 if (retval
!= ERROR_OK
)
1812 watchpoint
->is_set
= false;
1817 static int aarch64_add_watchpoint(struct target
*target
,
1818 struct watchpoint
*watchpoint
)
1821 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1823 if (aarch64
->wp_num_available
< 1) {
1824 LOG_INFO("no hardware watchpoint available");
1825 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1828 retval
= aarch64_set_watchpoint(target
, watchpoint
);
1829 if (retval
== ERROR_OK
)
1830 aarch64
->wp_num_available
--;
1835 static int aarch64_remove_watchpoint(struct target
*target
,
1836 struct watchpoint
*watchpoint
)
1838 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
1840 if (watchpoint
->is_set
) {
1841 aarch64_unset_watchpoint(target
, watchpoint
);
1842 aarch64
->wp_num_available
++;
1849 * find out which watchpoint hits
1850 * get exception address and compare the address to watchpoints
1852 int aarch64_hit_watchpoint(struct target
*target
,
1853 struct watchpoint
**hit_watchpoint
)
1855 if (target
->debug_reason
!= DBG_REASON_WATCHPOINT
)
1858 struct armv8_common
*armv8
= target_to_armv8(target
);
1860 target_addr_t exception_address
;
1861 struct watchpoint
*wp
;
1863 exception_address
= armv8
->dpm
.wp_addr
;
1865 if (exception_address
== 0xFFFFFFFF)
1868 for (wp
= target
->watchpoints
; wp
; wp
= wp
->next
)
1869 if (exception_address
>= wp
->address
&& exception_address
< (wp
->address
+ wp
->length
)) {
1870 *hit_watchpoint
= wp
;
1878 * Cortex-A8 Reset functions
1881 static int aarch64_enable_reset_catch(struct target
*target
, bool enable
)
1883 struct armv8_common
*armv8
= target_to_armv8(target
);
1887 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1888 armv8
->debug_base
+ CPUV8_DBG_EDECR
, &edecr
);
1889 LOG_DEBUG("EDECR = 0x%08" PRIx32
", enable=%d", edecr
, enable
);
1890 if (retval
!= ERROR_OK
)
1898 return mem_ap_write_atomic_u32(armv8
->debug_ap
,
1899 armv8
->debug_base
+ CPUV8_DBG_EDECR
, edecr
);
1902 static int aarch64_clear_reset_catch(struct target
*target
)
1904 struct armv8_common
*armv8
= target_to_armv8(target
);
1909 /* check if Reset Catch debug event triggered as expected */
1910 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
1911 armv8
->debug_base
+ CPUV8_DBG_EDESR
, &edesr
);
1912 if (retval
!= ERROR_OK
)
1915 was_triggered
= !!(edesr
& ESR_RC
);
1916 LOG_DEBUG("Reset Catch debug event %s",
1917 was_triggered
? "triggered" : "NOT triggered!");
1919 if (was_triggered
) {
1920 /* clear pending Reset Catch debug event */
1922 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
1923 armv8
->debug_base
+ CPUV8_DBG_EDESR
, edesr
);
1924 if (retval
!= ERROR_OK
)
1931 static int aarch64_assert_reset(struct target
*target
)
1933 struct armv8_common
*armv8
= target_to_armv8(target
);
1934 enum reset_types reset_config
= jtag_get_reset_config();
1939 /* Issue some kind of warm reset. */
1940 if (target_has_event_action(target
, TARGET_EVENT_RESET_ASSERT
))
1941 target_handle_event(target
, TARGET_EVENT_RESET_ASSERT
);
1942 else if (reset_config
& RESET_HAS_SRST
) {
1943 bool srst_asserted
= false;
1945 if (target
->reset_halt
&& !(reset_config
& RESET_SRST_PULLS_TRST
)) {
1946 if (target_was_examined(target
)) {
1948 if (reset_config
& RESET_SRST_NO_GATING
) {
1950 * SRST needs to be asserted *before* Reset Catch
1951 * debug event can be set up.
1953 adapter_assert_reset();
1954 srst_asserted
= true;
1957 /* make sure to clear all sticky errors */
1958 mem_ap_write_atomic_u32(armv8
->debug_ap
,
1959 armv8
->debug_base
+ CPUV8_DBG_DRCR
, DRCR_CSE
);
1961 /* set up Reset Catch debug event to halt the CPU after reset */
1962 retval
= aarch64_enable_reset_catch(target
, true);
1963 if (retval
!= ERROR_OK
)
1964 LOG_WARNING("%s: Error enabling Reset Catch debug event; the CPU will not halt immediately after reset!",
1965 target_name(target
));
1967 LOG_WARNING("%s: Target not examined, will not halt immediately after reset!",
1968 target_name(target
));
1972 /* REVISIT handle "pulls" cases, if there's
1973 * hardware that needs them to work.
1976 adapter_assert_reset();
1978 LOG_ERROR("%s: how to reset?", target_name(target
));
1982 /* registers are now invalid */
1983 if (target_was_examined(target
)) {
1984 register_cache_invalidate(armv8
->arm
.core_cache
);
1985 register_cache_invalidate(armv8
->arm
.core_cache
->next
);
1988 target
->state
= TARGET_RESET
;
1993 static int aarch64_deassert_reset(struct target
*target
)
1999 /* be certain SRST is off */
2000 adapter_deassert_reset();
2002 if (!target_was_examined(target
))
2005 retval
= aarch64_init_debug_access(target
);
2006 if (retval
!= ERROR_OK
)
2009 retval
= aarch64_poll(target
);
2010 if (retval
!= ERROR_OK
)
2013 if (target
->reset_halt
) {
2014 /* clear pending Reset Catch debug event */
2015 retval
= aarch64_clear_reset_catch(target
);
2016 if (retval
!= ERROR_OK
)
2017 LOG_WARNING("%s: Clearing Reset Catch debug event failed",
2018 target_name(target
));
2020 /* disable Reset Catch debug event */
2021 retval
= aarch64_enable_reset_catch(target
, false);
2022 if (retval
!= ERROR_OK
)
2023 LOG_WARNING("%s: Disabling Reset Catch debug event failed",
2024 target_name(target
));
2026 if (target
->state
!= TARGET_HALTED
) {
2027 LOG_WARNING("%s: ran after reset and before halt ...",
2028 target_name(target
));
2029 if (target_was_examined(target
)) {
2030 retval
= aarch64_halt_one(target
, HALT_LAZY
);
2031 if (retval
!= ERROR_OK
)
2034 target
->state
= TARGET_UNKNOWN
;
2042 static int aarch64_write_cpu_memory_slow(struct target
*target
,
2043 uint32_t size
, uint32_t count
, const uint8_t *buffer
, uint32_t *dscr
)
2045 struct armv8_common
*armv8
= target_to_armv8(target
);
2046 struct arm_dpm
*dpm
= &armv8
->dpm
;
2047 struct arm
*arm
= &armv8
->arm
;
2050 armv8_reg_current(arm
, 1)->dirty
= true;
2052 /* change DCC to normal mode if necessary */
2053 if (*dscr
& DSCR_MA
) {
2055 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2056 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2057 if (retval
!= ERROR_OK
)
2062 uint32_t data
, opcode
;
2064 /* write the data to store into DTRRX */
2068 data
= target_buffer_get_u16(target
, buffer
);
2070 data
= target_buffer_get_u32(target
, buffer
);
2071 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2072 armv8
->debug_base
+ CPUV8_DBG_DTRRX
, data
);
2073 if (retval
!= ERROR_OK
)
2076 if (arm
->core_state
== ARM_STATE_AARCH64
)
2077 retval
= dpm
->instr_execute(dpm
, ARMV8_MRS(SYSTEM_DBG_DTRRX_EL0
, 1));
2079 retval
= dpm
->instr_execute(dpm
, ARMV4_5_MRC(14, 0, 1, 0, 5, 0));
2080 if (retval
!= ERROR_OK
)
2084 opcode
= armv8_opcode(armv8
, ARMV8_OPC_STRB_IP
);
2086 opcode
= armv8_opcode(armv8
, ARMV8_OPC_STRH_IP
);
2088 opcode
= armv8_opcode(armv8
, ARMV8_OPC_STRW_IP
);
2089 retval
= dpm
->instr_execute(dpm
, opcode
);
2090 if (retval
!= ERROR_OK
)
2101 static int aarch64_write_cpu_memory_fast(struct target
*target
,
2102 uint32_t count
, const uint8_t *buffer
, uint32_t *dscr
)
2104 struct armv8_common
*armv8
= target_to_armv8(target
);
2105 struct arm
*arm
= &armv8
->arm
;
2108 armv8_reg_current(arm
, 1)->dirty
= true;
2110 /* Step 1.d - Change DCC to memory mode */
2112 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2113 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2114 if (retval
!= ERROR_OK
)
2118 /* Step 2.a - Do the write */
2119 retval
= mem_ap_write_buf_noincr(armv8
->debug_ap
,
2120 buffer
, 4, count
, armv8
->debug_base
+ CPUV8_DBG_DTRRX
);
2121 if (retval
!= ERROR_OK
)
2124 /* Step 3.a - Switch DTR mode back to Normal mode */
2126 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2127 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2128 if (retval
!= ERROR_OK
)
2134 static int aarch64_write_cpu_memory(struct target
*target
,
2135 uint64_t address
, uint32_t size
,
2136 uint32_t count
, const uint8_t *buffer
)
2138 /* write memory through APB-AP */
2139 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
2140 struct armv8_common
*armv8
= target_to_armv8(target
);
2141 struct arm_dpm
*dpm
= &armv8
->dpm
;
2142 struct arm
*arm
= &armv8
->arm
;
2145 if (target
->state
!= TARGET_HALTED
) {
2146 LOG_WARNING("target not halted");
2147 return ERROR_TARGET_NOT_HALTED
;
2150 /* Mark register X0 as dirty, as it will be used
2151 * for transferring the data.
2152 * It will be restored automatically when exiting
2155 armv8_reg_current(arm
, 0)->dirty
= true;
2157 /* This algorithm comes from DDI0487A.g, chapter J9.1 */
2160 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2161 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2162 if (retval
!= ERROR_OK
)
2165 /* Set Normal access mode */
2166 dscr
= (dscr
& ~DSCR_MA
);
2167 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2168 armv8
->debug_base
+ CPUV8_DBG_DSCR
, dscr
);
2169 if (retval
!= ERROR_OK
)
2172 if (arm
->core_state
== ARM_STATE_AARCH64
) {
2173 /* Write X0 with value 'address' using write procedure */
2174 /* Step 1.a+b - Write the address for read access into DBGDTR_EL0 */
2175 /* Step 1.c - Copy value from DTR to R0 using instruction mrs DBGDTR_EL0, x0 */
2176 retval
= dpm
->instr_write_data_dcc_64(dpm
,
2177 ARMV8_MRS(SYSTEM_DBG_DBGDTR_EL0
, 0), address
);
2179 /* Write R0 with value 'address' using write procedure */
2180 /* Step 1.a+b - Write the address for read access into DBGDTRRX */
2181 /* Step 1.c - Copy value from DTR to R0 using instruction mrc DBGDTRTXint, r0 */
2182 retval
= dpm
->instr_write_data_dcc(dpm
,
2183 ARMV4_5_MRC(14, 0, 0, 0, 5, 0), address
);
2186 if (retval
!= ERROR_OK
)
2189 if (size
== 4 && (address
% 4) == 0)
2190 retval
= aarch64_write_cpu_memory_fast(target
, count
, buffer
, &dscr
);
2192 retval
= aarch64_write_cpu_memory_slow(target
, size
, count
, buffer
, &dscr
);
2194 if (retval
!= ERROR_OK
) {
2195 /* Unset DTR mode */
2196 mem_ap_read_atomic_u32(armv8
->debug_ap
,
2197 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2199 mem_ap_write_atomic_u32(armv8
->debug_ap
,
2200 armv8
->debug_base
+ CPUV8_DBG_DSCR
, dscr
);
2203 /* Check for sticky abort flags in the DSCR */
2204 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2205 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2206 if (retval
!= ERROR_OK
)
2210 if (dscr
& (DSCR_ERR
| DSCR_SYS_ERROR_PEND
)) {
2211 /* Abort occurred - clear it and exit */
2212 LOG_ERROR("abort occurred - dscr = 0x%08" PRIx32
, dscr
);
2213 armv8_dpm_handle_exception(dpm
, true);
2221 static int aarch64_read_cpu_memory_slow(struct target
*target
,
2222 uint32_t size
, uint32_t count
, uint8_t *buffer
, uint32_t *dscr
)
2224 struct armv8_common
*armv8
= target_to_armv8(target
);
2225 struct arm_dpm
*dpm
= &armv8
->dpm
;
2226 struct arm
*arm
= &armv8
->arm
;
2229 armv8_reg_current(arm
, 1)->dirty
= true;
2231 /* change DCC to normal mode (if necessary) */
2232 if (*dscr
& DSCR_MA
) {
2234 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2235 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2236 if (retval
!= ERROR_OK
)
2241 uint32_t opcode
, data
;
2244 opcode
= armv8_opcode(armv8
, ARMV8_OPC_LDRB_IP
);
2246 opcode
= armv8_opcode(armv8
, ARMV8_OPC_LDRH_IP
);
2248 opcode
= armv8_opcode(armv8
, ARMV8_OPC_LDRW_IP
);
2249 retval
= dpm
->instr_execute(dpm
, opcode
);
2250 if (retval
!= ERROR_OK
)
2253 if (arm
->core_state
== ARM_STATE_AARCH64
)
2254 retval
= dpm
->instr_execute(dpm
, ARMV8_MSR_GP(SYSTEM_DBG_DTRTX_EL0
, 1));
2256 retval
= dpm
->instr_execute(dpm
, ARMV4_5_MCR(14, 0, 1, 0, 5, 0));
2257 if (retval
!= ERROR_OK
)
2260 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2261 armv8
->debug_base
+ CPUV8_DBG_DTRTX
, &data
);
2262 if (retval
!= ERROR_OK
)
2266 *buffer
= (uint8_t)data
;
2268 target_buffer_set_u16(target
, buffer
, (uint16_t)data
);
2270 target_buffer_set_u32(target
, buffer
, data
);
2280 static int aarch64_read_cpu_memory_fast(struct target
*target
,
2281 uint32_t count
, uint8_t *buffer
, uint32_t *dscr
)
2283 struct armv8_common
*armv8
= target_to_armv8(target
);
2284 struct arm_dpm
*dpm
= &armv8
->dpm
;
2285 struct arm
*arm
= &armv8
->arm
;
2289 /* Mark X1 as dirty */
2290 armv8_reg_current(arm
, 1)->dirty
= true;
2292 if (arm
->core_state
== ARM_STATE_AARCH64
) {
2293 /* Step 1.d - Dummy operation to ensure EDSCR.Txfull == 1 */
2294 retval
= dpm
->instr_execute(dpm
, ARMV8_MSR_GP(SYSTEM_DBG_DBGDTR_EL0
, 0));
2296 /* Step 1.d - Dummy operation to ensure EDSCR.Txfull == 1 */
2297 retval
= dpm
->instr_execute(dpm
, ARMV4_5_MCR(14, 0, 0, 0, 5, 0));
2300 if (retval
!= ERROR_OK
)
2303 /* Step 1.e - Change DCC to memory mode */
2305 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2306 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2307 if (retval
!= ERROR_OK
)
2310 /* Step 1.f - read DBGDTRTX and discard the value */
2311 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2312 armv8
->debug_base
+ CPUV8_DBG_DTRTX
, &value
);
2313 if (retval
!= ERROR_OK
)
2317 /* Read the data - Each read of the DTRTX register causes the instruction to be reissued
2318 * Abort flags are sticky, so can be read at end of transactions
2320 * This data is read in aligned to 32 bit boundary.
2324 /* Step 2.a - Loop n-1 times, each read of DBGDTRTX reads the data from [X0] and
2325 * increments X0 by 4. */
2326 retval
= mem_ap_read_buf_noincr(armv8
->debug_ap
, buffer
, 4, count
,
2327 armv8
->debug_base
+ CPUV8_DBG_DTRTX
);
2328 if (retval
!= ERROR_OK
)
2332 /* Step 3.a - set DTR access mode back to Normal mode */
2334 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2335 armv8
->debug_base
+ CPUV8_DBG_DSCR
, *dscr
);
2336 if (retval
!= ERROR_OK
)
2339 /* Step 3.b - read DBGDTRTX for the final value */
2340 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2341 armv8
->debug_base
+ CPUV8_DBG_DTRTX
, &value
);
2342 if (retval
!= ERROR_OK
)
2345 target_buffer_set_u32(target
, buffer
+ count
* 4, value
);
2349 static int aarch64_read_cpu_memory(struct target
*target
,
2350 target_addr_t address
, uint32_t size
,
2351 uint32_t count
, uint8_t *buffer
)
2353 /* read memory through APB-AP */
2354 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
2355 struct armv8_common
*armv8
= target_to_armv8(target
);
2356 struct arm_dpm
*dpm
= &armv8
->dpm
;
2357 struct arm
*arm
= &armv8
->arm
;
2360 LOG_DEBUG("Reading CPU memory address 0x%016" PRIx64
" size %" PRIu32
" count %" PRIu32
,
2361 address
, size
, count
);
2363 if (target
->state
!= TARGET_HALTED
) {
2364 LOG_WARNING("target not halted");
2365 return ERROR_TARGET_NOT_HALTED
;
2368 /* Mark register X0 as dirty, as it will be used
2369 * for transferring the data.
2370 * It will be restored automatically when exiting
2373 armv8_reg_current(arm
, 0)->dirty
= true;
2376 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2377 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2378 if (retval
!= ERROR_OK
)
2381 /* This algorithm comes from DDI0487A.g, chapter J9.1 */
2383 /* Set Normal access mode */
2385 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2386 armv8
->debug_base
+ CPUV8_DBG_DSCR
, dscr
);
2387 if (retval
!= ERROR_OK
)
2390 if (arm
->core_state
== ARM_STATE_AARCH64
) {
2391 /* Write X0 with value 'address' using write procedure */
2392 /* Step 1.a+b - Write the address for read access into DBGDTR_EL0 */
2393 /* Step 1.c - Copy value from DTR to R0 using instruction mrs DBGDTR_EL0, x0 */
2394 retval
= dpm
->instr_write_data_dcc_64(dpm
,
2395 ARMV8_MRS(SYSTEM_DBG_DBGDTR_EL0
, 0), address
);
2397 /* Write R0 with value 'address' using write procedure */
2398 /* Step 1.a+b - Write the address for read access into DBGDTRRXint */
2399 /* Step 1.c - Copy value from DTR to R0 using instruction mrc DBGDTRTXint, r0 */
2400 retval
= dpm
->instr_write_data_dcc(dpm
,
2401 ARMV4_5_MRC(14, 0, 0, 0, 5, 0), address
);
2404 if (retval
!= ERROR_OK
)
2407 if (size
== 4 && (address
% 4) == 0)
2408 retval
= aarch64_read_cpu_memory_fast(target
, count
, buffer
, &dscr
);
2410 retval
= aarch64_read_cpu_memory_slow(target
, size
, count
, buffer
, &dscr
);
2412 if (dscr
& DSCR_MA
) {
2414 mem_ap_write_atomic_u32(armv8
->debug_ap
,
2415 armv8
->debug_base
+ CPUV8_DBG_DSCR
, dscr
);
2418 if (retval
!= ERROR_OK
)
2421 /* Check for sticky abort flags in the DSCR */
2422 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2423 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2424 if (retval
!= ERROR_OK
)
2429 if (dscr
& (DSCR_ERR
| DSCR_SYS_ERROR_PEND
)) {
2430 /* Abort occurred - clear it and exit */
2431 LOG_ERROR("abort occurred - dscr = 0x%08" PRIx32
, dscr
);
2432 armv8_dpm_handle_exception(dpm
, true);
2440 static int aarch64_read_phys_memory(struct target
*target
,
2441 target_addr_t address
, uint32_t size
,
2442 uint32_t count
, uint8_t *buffer
)
2444 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
2446 if (count
&& buffer
) {
2447 /* read memory through APB-AP */
2448 retval
= aarch64_mmu_modify(target
, 0);
2449 if (retval
!= ERROR_OK
)
2451 retval
= aarch64_read_cpu_memory(target
, address
, size
, count
, buffer
);
2456 static int aarch64_read_memory(struct target
*target
, target_addr_t address
,
2457 uint32_t size
, uint32_t count
, uint8_t *buffer
)
2459 int mmu_enabled
= 0;
2462 /* determine if MMU was enabled on target stop */
2463 retval
= aarch64_mmu(target
, &mmu_enabled
);
2464 if (retval
!= ERROR_OK
)
2468 /* enable MMU as we could have disabled it for phys access */
2469 retval
= aarch64_mmu_modify(target
, 1);
2470 if (retval
!= ERROR_OK
)
2473 return aarch64_read_cpu_memory(target
, address
, size
, count
, buffer
);
2476 static int aarch64_write_phys_memory(struct target
*target
,
2477 target_addr_t address
, uint32_t size
,
2478 uint32_t count
, const uint8_t *buffer
)
2480 int retval
= ERROR_COMMAND_SYNTAX_ERROR
;
2482 if (count
&& buffer
) {
2483 /* write memory through APB-AP */
2484 retval
= aarch64_mmu_modify(target
, 0);
2485 if (retval
!= ERROR_OK
)
2487 return aarch64_write_cpu_memory(target
, address
, size
, count
, buffer
);
2493 static int aarch64_write_memory(struct target
*target
, target_addr_t address
,
2494 uint32_t size
, uint32_t count
, const uint8_t *buffer
)
2496 int mmu_enabled
= 0;
2499 /* determine if MMU was enabled on target stop */
2500 retval
= aarch64_mmu(target
, &mmu_enabled
);
2501 if (retval
!= ERROR_OK
)
2505 /* enable MMU as we could have disabled it for phys access */
2506 retval
= aarch64_mmu_modify(target
, 1);
2507 if (retval
!= ERROR_OK
)
2510 return aarch64_write_cpu_memory(target
, address
, size
, count
, buffer
);
2513 static int aarch64_handle_target_request(void *priv
)
2515 struct target
*target
= priv
;
2516 struct armv8_common
*armv8
= target_to_armv8(target
);
2519 if (!target_was_examined(target
))
2521 if (!target
->dbg_msg_enabled
)
2524 if (target
->state
== TARGET_RUNNING
) {
2527 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2528 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2530 /* check if we have data */
2531 while ((dscr
& DSCR_DTR_TX_FULL
) && (retval
== ERROR_OK
)) {
2532 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2533 armv8
->debug_base
+ CPUV8_DBG_DTRTX
, &request
);
2534 if (retval
== ERROR_OK
) {
2535 target_request(target
, request
);
2536 retval
= mem_ap_read_atomic_u32(armv8
->debug_ap
,
2537 armv8
->debug_base
+ CPUV8_DBG_DSCR
, &dscr
);
2545 static int aarch64_examine_first(struct target
*target
)
2547 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
2548 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
2549 struct adiv5_dap
*swjdp
= armv8
->arm
.dap
;
2550 struct aarch64_private_config
*pc
= target
->private_config
;
2552 int retval
= ERROR_OK
;
2553 uint64_t debug
, ttypr
;
2555 uint32_t tmp0
, tmp1
, tmp2
, tmp3
;
2556 debug
= ttypr
= cpuid
= 0;
2561 if (armv8
->debug_ap
) {
2562 dap_put_ap(armv8
->debug_ap
);
2563 armv8
->debug_ap
= NULL
;
2566 if (pc
->adiv5_config
.ap_num
== DP_APSEL_INVALID
) {
2567 /* Search for the APB-AB */
2568 retval
= dap_find_get_ap(swjdp
, AP_TYPE_APB_AP
, &armv8
->debug_ap
);
2569 if (retval
!= ERROR_OK
) {
2570 LOG_ERROR("Could not find APB-AP for debug access");
2574 armv8
->debug_ap
= dap_get_ap(swjdp
, pc
->adiv5_config
.ap_num
);
2575 if (!armv8
->debug_ap
) {
2576 LOG_ERROR("Cannot get AP");
2581 retval
= mem_ap_init(armv8
->debug_ap
);
2582 if (retval
!= ERROR_OK
) {
2583 LOG_ERROR("Could not initialize the APB-AP");
2587 armv8
->debug_ap
->memaccess_tck
= 10;
2589 if (!target
->dbgbase_set
) {
2590 /* Lookup Processor DAP */
2591 retval
= dap_lookup_cs_component(armv8
->debug_ap
, ARM_CS_C9_DEVTYPE_CORE_DEBUG
,
2592 &armv8
->debug_base
, target
->coreid
);
2593 if (retval
!= ERROR_OK
)
2595 LOG_DEBUG("Detected core %" PRId32
" dbgbase: " TARGET_ADDR_FMT
,
2596 target
->coreid
, armv8
->debug_base
);
2598 armv8
->debug_base
= target
->dbgbase
;
2600 retval
= mem_ap_write_atomic_u32(armv8
->debug_ap
,
2601 armv8
->debug_base
+ CPUV8_DBG_OSLAR
, 0);
2602 if (retval
!= ERROR_OK
) {
2603 LOG_DEBUG("Examine %s failed", "oslock");
2607 retval
= mem_ap_read_u32(armv8
->debug_ap
,
2608 armv8
->debug_base
+ CPUV8_DBG_MAINID0
, &cpuid
);
2609 if (retval
!= ERROR_OK
) {
2610 LOG_DEBUG("Examine %s failed", "CPUID");
2614 retval
= mem_ap_read_u32(armv8
->debug_ap
,
2615 armv8
->debug_base
+ CPUV8_DBG_MEMFEATURE0
, &tmp0
);
2616 retval
+= mem_ap_read_u32(armv8
->debug_ap
,
2617 armv8
->debug_base
+ CPUV8_DBG_MEMFEATURE0
+ 4, &tmp1
);
2618 if (retval
!= ERROR_OK
) {
2619 LOG_DEBUG("Examine %s failed", "Memory Model Type");
2622 retval
= mem_ap_read_u32(armv8
->debug_ap
,
2623 armv8
->debug_base
+ CPUV8_DBG_DBGFEATURE0
, &tmp2
);
2624 retval
+= mem_ap_read_u32(armv8
->debug_ap
,
2625 armv8
->debug_base
+ CPUV8_DBG_DBGFEATURE0
+ 4, &tmp3
);
2626 if (retval
!= ERROR_OK
) {
2627 LOG_DEBUG("Examine %s failed", "ID_AA64DFR0_EL1");
2631 retval
= dap_run(armv8
->debug_ap
->dap
);
2632 if (retval
!= ERROR_OK
) {
2633 LOG_ERROR("%s: examination failed\n", target_name(target
));
2638 ttypr
= (ttypr
<< 32) | tmp0
;
2640 debug
= (debug
<< 32) | tmp2
;
2642 LOG_DEBUG("cpuid = 0x%08" PRIx32
, cpuid
);
2643 LOG_DEBUG("ttypr = 0x%08" PRIx64
, ttypr
);
2644 LOG_DEBUG("debug = 0x%08" PRIx64
, debug
);
2647 LOG_TARGET_ERROR(target
, "CTI not specified");
2651 armv8
->cti
= pc
->cti
;
2653 retval
= aarch64_dpm_setup(aarch64
, debug
);
2654 if (retval
!= ERROR_OK
)
2657 /* Setup Breakpoint Register Pairs */
2658 aarch64
->brp_num
= (uint32_t)((debug
>> 12) & 0x0F) + 1;
2659 aarch64
->brp_num_context
= (uint32_t)((debug
>> 28) & 0x0F) + 1;
2660 aarch64
->brp_num_available
= aarch64
->brp_num
;
2661 aarch64
->brp_list
= calloc(aarch64
->brp_num
, sizeof(struct aarch64_brp
));
2662 for (i
= 0; i
< aarch64
->brp_num
; i
++) {
2663 aarch64
->brp_list
[i
].used
= 0;
2664 if (i
< (aarch64
->brp_num
-aarch64
->brp_num_context
))
2665 aarch64
->brp_list
[i
].type
= BRP_NORMAL
;
2667 aarch64
->brp_list
[i
].type
= BRP_CONTEXT
;
2668 aarch64
->brp_list
[i
].value
= 0;
2669 aarch64
->brp_list
[i
].control
= 0;
2670 aarch64
->brp_list
[i
].brpn
= i
;
2673 /* Setup Watchpoint Register Pairs */
2674 aarch64
->wp_num
= (uint32_t)((debug
>> 20) & 0x0F) + 1;
2675 aarch64
->wp_num_available
= aarch64
->wp_num
;
2676 aarch64
->wp_list
= calloc(aarch64
->wp_num
, sizeof(struct aarch64_brp
));
2677 for (i
= 0; i
< aarch64
->wp_num
; i
++) {
2678 aarch64
->wp_list
[i
].used
= 0;
2679 aarch64
->wp_list
[i
].type
= BRP_NORMAL
;
2680 aarch64
->wp_list
[i
].value
= 0;
2681 aarch64
->wp_list
[i
].control
= 0;
2682 aarch64
->wp_list
[i
].brpn
= i
;
2685 LOG_DEBUG("Configured %i hw breakpoints, %i watchpoints",
2686 aarch64
->brp_num
, aarch64
->wp_num
);
2688 target
->state
= TARGET_UNKNOWN
;
2689 target
->debug_reason
= DBG_REASON_NOTHALTED
;
2690 aarch64
->isrmasking_mode
= AARCH64_ISRMASK_ON
;
2691 target_set_examined(target
);
2695 static int aarch64_examine(struct target
*target
)
2697 int retval
= ERROR_OK
;
2699 /* don't re-probe hardware after each reset */
2700 if (!target_was_examined(target
))
2701 retval
= aarch64_examine_first(target
);
2703 /* Configure core debug access */
2704 if (retval
== ERROR_OK
)
2705 retval
= aarch64_init_debug_access(target
);
2711 * Cortex-A8 target creation and initialization
2714 static int aarch64_init_target(struct command_context
*cmd_ctx
,
2715 struct target
*target
)
2717 /* examine_first() does a bunch of this */
2718 arm_semihosting_init(target
);
2722 static int aarch64_init_arch_info(struct target
*target
,
2723 struct aarch64_common
*aarch64
, struct adiv5_dap
*dap
)
2725 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
2727 /* Setup struct aarch64_common */
2728 aarch64
->common_magic
= AARCH64_COMMON_MAGIC
;
2729 armv8
->arm
.dap
= dap
;
2731 /* register arch-specific functions */
2732 armv8
->examine_debug_reason
= NULL
;
2733 armv8
->post_debug_entry
= aarch64_post_debug_entry
;
2734 armv8
->pre_restore_context
= NULL
;
2735 armv8
->armv8_mmu
.read_physical_memory
= aarch64_read_phys_memory
;
2737 armv8_init_arch_info(target
, armv8
);
2738 target_register_timer_callback(aarch64_handle_target_request
, 1,
2739 TARGET_TIMER_TYPE_PERIODIC
, target
);
2744 static int aarch64_target_create(struct target
*target
, Jim_Interp
*interp
)
2746 struct aarch64_private_config
*pc
= target
->private_config
;
2747 struct aarch64_common
*aarch64
;
2749 if (adiv5_verify_config(&pc
->adiv5_config
) != ERROR_OK
)
2752 aarch64
= calloc(1, sizeof(struct aarch64_common
));
2754 LOG_ERROR("Out of memory");
2758 return aarch64_init_arch_info(target
, aarch64
, pc
->adiv5_config
.dap
);
2761 static void aarch64_deinit_target(struct target
*target
)
2763 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
2764 struct armv8_common
*armv8
= &aarch64
->armv8_common
;
2765 struct arm_dpm
*dpm
= &armv8
->dpm
;
2767 if (armv8
->debug_ap
)
2768 dap_put_ap(armv8
->debug_ap
);
2770 armv8_free_reg_cache(target
);
2771 free(aarch64
->brp_list
);
2774 free(target
->private_config
);
2778 static int aarch64_mmu(struct target
*target
, int *enabled
)
2780 if (target
->state
!= TARGET_HALTED
) {
2781 LOG_ERROR("%s: target %s not halted", __func__
, target_name(target
));
2782 return ERROR_TARGET_INVALID
;
2785 *enabled
= target_to_aarch64(target
)->armv8_common
.armv8_mmu
.mmu_enabled
;
2789 static int aarch64_virt2phys(struct target
*target
, target_addr_t virt
,
2790 target_addr_t
*phys
)
2792 return armv8_mmu_translate_va_pa(target
, virt
, phys
, 1);
2796 * private target configuration items
2798 enum aarch64_cfg_param
{
2802 static const struct jim_nvp nvp_config_opts
[] = {
2803 { .name
= "-cti", .value
= CFG_CTI
},
2804 { .name
= NULL
, .value
= -1 }
2807 static int aarch64_jim_configure(struct target
*target
, struct jim_getopt_info
*goi
)
2809 struct aarch64_private_config
*pc
;
2813 pc
= (struct aarch64_private_config
*)target
->private_config
;
2815 pc
= calloc(1, sizeof(struct aarch64_private_config
));
2816 pc
->adiv5_config
.ap_num
= DP_APSEL_INVALID
;
2817 target
->private_config
= pc
;
2821 * Call adiv5_jim_configure() to parse the common DAP options
2822 * It will return JIM_CONTINUE if it didn't find any known
2823 * options, JIM_OK if it correctly parsed the topmost option
2824 * and JIM_ERR if an error occurred during parameter evaluation.
2825 * For JIM_CONTINUE, we check our own params.
2827 * adiv5_jim_configure() assumes 'private_config' to point to
2828 * 'struct adiv5_private_config'. Override 'private_config'!
2830 target
->private_config
= &pc
->adiv5_config
;
2831 e
= adiv5_jim_configure(target
, goi
);
2832 target
->private_config
= pc
;
2833 if (e
!= JIM_CONTINUE
)
2836 /* parse config or cget options ... */
2837 if (goi
->argc
> 0) {
2838 Jim_SetEmptyResult(goi
->interp
);
2840 /* check first if topmost item is for us */
2841 e
= jim_nvp_name2value_obj(goi
->interp
, nvp_config_opts
,
2844 return JIM_CONTINUE
;
2846 e
= jim_getopt_obj(goi
, NULL
);
2852 if (goi
->isconfigure
) {
2854 struct arm_cti
*cti
;
2855 e
= jim_getopt_obj(goi
, &o_cti
);
2858 cti
= cti_instance_by_jim_obj(goi
->interp
, o_cti
);
2860 Jim_SetResultString(goi
->interp
, "CTI name invalid!", -1);
2865 if (goi
->argc
!= 0) {
2866 Jim_WrongNumArgs(goi
->interp
,
2867 goi
->argc
, goi
->argv
,
2872 if (!pc
|| !pc
->cti
) {
2873 Jim_SetResultString(goi
->interp
, "CTI not configured", -1);
2876 Jim_SetResultString(goi
->interp
, arm_cti_name(pc
->cti
), -1);
2882 return JIM_CONTINUE
;
2889 COMMAND_HANDLER(aarch64_handle_cache_info_command
)
2891 struct target
*target
= get_current_target(CMD_CTX
);
2892 struct armv8_common
*armv8
= target_to_armv8(target
);
2894 return armv8_handle_cache_info_command(CMD
,
2895 &armv8
->armv8_mmu
.armv8_cache
);
2898 COMMAND_HANDLER(aarch64_handle_dbginit_command
)
2900 struct target
*target
= get_current_target(CMD_CTX
);
2901 if (!target_was_examined(target
)) {
2902 LOG_ERROR("target not examined yet");
2906 return aarch64_init_debug_access(target
);
2909 COMMAND_HANDLER(aarch64_handle_disassemble_command
)
2911 struct target
*target
= get_current_target(CMD_CTX
);
2914 LOG_ERROR("No target selected");
2918 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
2920 if (aarch64
->common_magic
!= AARCH64_COMMON_MAGIC
) {
2921 command_print(CMD
, "current target isn't an AArch64");
2926 target_addr_t address
;
2930 COMMAND_PARSE_NUMBER(int, CMD_ARGV
[1], count
);
2933 COMMAND_PARSE_ADDRESS(CMD_ARGV
[0], address
);
2936 return ERROR_COMMAND_SYNTAX_ERROR
;
2939 return a64_disassemble(CMD
, target
, address
, count
);
2942 COMMAND_HANDLER(aarch64_mask_interrupts_command
)
2944 struct target
*target
= get_current_target(CMD_CTX
);
2945 struct aarch64_common
*aarch64
= target_to_aarch64(target
);
2947 static const struct jim_nvp nvp_maskisr_modes
[] = {
2948 { .name
= "off", .value
= AARCH64_ISRMASK_OFF
},
2949 { .name
= "on", .value
= AARCH64_ISRMASK_ON
},
2950 { .name
= NULL
, .value
= -1 },
2952 const struct jim_nvp
*n
;
2955 n
= jim_nvp_name2value_simple(nvp_maskisr_modes
, CMD_ARGV
[0]);
2957 LOG_ERROR("Unknown parameter: %s - should be off or on", CMD_ARGV
[0]);
2958 return ERROR_COMMAND_SYNTAX_ERROR
;
2961 aarch64
->isrmasking_mode
= n
->value
;
2964 n
= jim_nvp_value2name_simple(nvp_maskisr_modes
, aarch64
->isrmasking_mode
);
2965 command_print(CMD
, "aarch64 interrupt mask %s", n
->name
);
2970 static int jim_mcrmrc(Jim_Interp
*interp
, int argc
, Jim_Obj
* const *argv
)
2972 struct command
*c
= jim_to_command(interp
);
2973 struct command_context
*context
;
2974 struct target
*target
;
2977 bool is_mcr
= false;
2980 if (!strcmp(c
->name
, "mcr")) {
2987 context
= current_command_context(interp
);
2990 target
= get_current_target(context
);
2992 LOG_ERROR("%s: no current target", __func__
);
2995 if (!target_was_examined(target
)) {
2996 LOG_ERROR("%s: not yet examined", target_name(target
));
3000 arm
= target_to_arm(target
);
3002 LOG_ERROR("%s: not an ARM", target_name(target
));
3006 if (target
->state
!= TARGET_HALTED
)
3007 return ERROR_TARGET_NOT_HALTED
;
3009 if (arm
->core_state
== ARM_STATE_AARCH64
) {
3010 LOG_ERROR("%s: not 32-bit arm target", target_name(target
));
3014 if (argc
!= arg_cnt
) {
3015 LOG_ERROR("%s: wrong number of arguments", __func__
);
3027 /* NOTE: parameter sequence matches ARM instruction set usage:
3028 * MCR pNUM, op1, rX, CRn, CRm, op2 ; write CP from rX
3029 * MRC pNUM, op1, rX, CRn, CRm, op2 ; read CP into rX
3030 * The "rX" is necessarily omitted; it uses Tcl mechanisms.
3032 retval
= Jim_GetLong(interp
, argv
[1], &l
);
3033 if (retval
!= JIM_OK
)
3036 LOG_ERROR("%s: %s %d out of range", __func__
,
3037 "coprocessor", (int) l
);
3042 retval
= Jim_GetLong(interp
, argv
[2], &l
);
3043 if (retval
!= JIM_OK
)
3046 LOG_ERROR("%s: %s %d out of range", __func__
,
3052 retval
= Jim_GetLong(interp
, argv
[3], &l
);
3053 if (retval
!= JIM_OK
)
3056 LOG_ERROR("%s: %s %d out of range", __func__
,
3062 retval
= Jim_GetLong(interp
, argv
[4], &l
);
3063 if (retval
!= JIM_OK
)
3066 LOG_ERROR("%s: %s %d out of range", __func__
,
3072 retval
= Jim_GetLong(interp
, argv
[5], &l
);
3073 if (retval
!= JIM_OK
)
3076 LOG_ERROR("%s: %s %d out of range", __func__
,
3084 if (is_mcr
== true) {
3085 retval
= Jim_GetLong(interp
, argv
[6], &l
);
3086 if (retval
!= JIM_OK
)
3090 /* NOTE: parameters reordered! */
3091 /* ARMV4_5_MCR(cpnum, op1, 0, crn, crm, op2) */
3092 retval
= arm
->mcr(target
, cpnum
, op1
, op2
, crn
, crm
, value
);
3093 if (retval
!= ERROR_OK
)
3096 /* NOTE: parameters reordered! */
3097 /* ARMV4_5_MRC(cpnum, op1, 0, crn, crm, op2) */
3098 retval
= arm
->mrc(target
, cpnum
, op1
, op2
, crn
, crm
, &value
);
3099 if (retval
!= ERROR_OK
)
3102 Jim_SetResult(interp
, Jim_NewIntObj(interp
, value
));
3108 static const struct command_registration aarch64_exec_command_handlers
[] = {
3110 .name
= "cache_info",
3111 .handler
= aarch64_handle_cache_info_command
,
3112 .mode
= COMMAND_EXEC
,
3113 .help
= "display information about target caches",
3118 .handler
= aarch64_handle_dbginit_command
,
3119 .mode
= COMMAND_EXEC
,
3120 .help
= "Initialize core debug",
3124 .name
= "disassemble",
3125 .handler
= aarch64_handle_disassemble_command
,
3126 .mode
= COMMAND_EXEC
,
3127 .help
= "Disassemble instructions",
3128 .usage
= "address [count]",
3132 .handler
= aarch64_mask_interrupts_command
,
3133 .mode
= COMMAND_ANY
,
3134 .help
= "mask aarch64 interrupts during single-step",
3135 .usage
= "['on'|'off']",
3139 .mode
= COMMAND_EXEC
,
3140 .jim_handler
= jim_mcrmrc
,
3141 .help
= "write coprocessor register",
3142 .usage
= "cpnum op1 CRn CRm op2 value",
3146 .mode
= COMMAND_EXEC
,
3147 .jim_handler
= jim_mcrmrc
,
3148 .help
= "read coprocessor register",
3149 .usage
= "cpnum op1 CRn CRm op2",
3152 .chain
= smp_command_handlers
,
3156 COMMAND_REGISTRATION_DONE
3159 extern const struct command_registration semihosting_common_handlers
[];
3161 static const struct command_registration aarch64_command_handlers
[] = {
3164 .mode
= COMMAND_ANY
,
3165 .help
= "ARM Command Group",
3167 .chain
= semihosting_common_handlers
3170 .chain
= armv8_command_handlers
,
3174 .mode
= COMMAND_ANY
,
3175 .help
= "Aarch64 command group",
3177 .chain
= aarch64_exec_command_handlers
,
3179 COMMAND_REGISTRATION_DONE
3182 struct target_type aarch64_target
= {
3185 .poll
= aarch64_poll
,
3186 .arch_state
= armv8_arch_state
,
3188 .halt
= aarch64_halt
,
3189 .resume
= aarch64_resume
,
3190 .step
= aarch64_step
,
3192 .assert_reset
= aarch64_assert_reset
,
3193 .deassert_reset
= aarch64_deassert_reset
,
3195 /* REVISIT allow exporting VFP3 registers ... */
3196 .get_gdb_arch
= armv8_get_gdb_arch
,
3197 .get_gdb_reg_list
= armv8_get_gdb_reg_list
,
3199 .read_memory
= aarch64_read_memory
,
3200 .write_memory
= aarch64_write_memory
,
3202 .add_breakpoint
= aarch64_add_breakpoint
,
3203 .add_context_breakpoint
= aarch64_add_context_breakpoint
,
3204 .add_hybrid_breakpoint
= aarch64_add_hybrid_breakpoint
,
3205 .remove_breakpoint
= aarch64_remove_breakpoint
,
3206 .add_watchpoint
= aarch64_add_watchpoint
,
3207 .remove_watchpoint
= aarch64_remove_watchpoint
,
3208 .hit_watchpoint
= aarch64_hit_watchpoint
,
3210 .commands
= aarch64_command_handlers
,
3211 .target_create
= aarch64_target_create
,
3212 .target_jim_configure
= aarch64_jim_configure
,
3213 .init_target
= aarch64_init_target
,
3214 .deinit_target
= aarch64_deinit_target
,
3215 .examine
= aarch64_examine
,
3217 .read_phys_memory
= aarch64_read_phys_memory
,
3218 .write_phys_memory
= aarch64_write_phys_memory
,
3220 .virt2phys
= aarch64_virt2phys
,