]> git.sur5r.net Git - openocd/blobdiff - src/target/cortex_a.c
target/arm_dpm: uniform names of exported functions
[openocd] / src / target / cortex_a.c
index e4d8331b291bb721258c77fdbe14229e434fb7ab..77859d3e861b70b574adb3598668bd0511e83b5f 100644 (file)
@@ -57,6 +57,9 @@
 #include "transport/transport.h"
 #include <helper/time_support.h>
 
+#define foreach_smp_target(pos, head) \
+       for (pos = head; (pos != NULL); pos = pos->next)
+
 static int cortex_a_poll(struct target *target);
 static int cortex_a_debug_entry(struct target *target);
 static int cortex_a_restore_context(struct target *target, bool bpwp);
@@ -110,7 +113,7 @@ static int cortex_a_prep_memaccess(struct target *target, int phys_access)
        int mmu_enabled = 0;
 
        if (phys_access == 0) {
-               dpm_modeswitch(&armv7a->dpm, ARM_MODE_SVC);
+               arm_dpm_modeswitch(&armv7a->dpm, ARM_MODE_SVC);
                cortex_a_mmu(target, &mmu_enabled);
                if (mmu_enabled)
                        cortex_a_mmu_modify(target, 1);
@@ -145,7 +148,7 @@ static int cortex_a_post_memaccess(struct target *target, int phys_access)
                                        0, 0, 3, 0,
                                        cortex_a->cp15_dacr_reg);
                }
-               dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
+               arm_dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
        } else {
                int mmu_enabled = 0;
                cortex_a_mmu(target, &mmu_enabled);
@@ -304,32 +307,6 @@ static int cortex_a_exec_opcode(struct target *target,
        return retval;
 }
 
-/**************************************************************************
-Read core register with very few exec_opcode, fast but needs work_area.
-This can cause problems with MMU active.
-**************************************************************************/
-static int cortex_a_read_regs_through_mem(struct target *target, uint32_t address,
-       uint32_t *regfile)
-{
-       int retval = ERROR_OK;
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-
-       retval = cortex_a_dap_read_coreregister_u32(target, regfile, 0);
-       if (retval != ERROR_OK)
-               return retval;
-       retval = cortex_a_dap_write_coreregister_u32(target, address, 0);
-       if (retval != ERROR_OK)
-               return retval;
-       retval = cortex_a_exec_opcode(target, ARMV4_5_STMIA(0, 0xFFFE, 0, 0), NULL);
-       if (retval != ERROR_OK)
-               return retval;
-
-       retval = mem_ap_read_buf(armv7a->memory_ap,
-                       (uint8_t *)(&regfile[1]), 4, 15, address);
-
-       return retval;
-}
-
 static int cortex_a_dap_read_coreregister_u32(struct target *target,
        uint32_t *value, int regnum)
 {
@@ -392,6 +369,7 @@ static int cortex_a_dap_read_coreregister_u32(struct target *target,
        return retval;
 }
 
+__attribute__((unused))
 static int cortex_a_dap_write_coreregister_u32(struct target *target,
        uint32_t value, int regnum)
 {
@@ -806,12 +784,43 @@ static int cortex_a_halt_smp(struct target *target)
 
 static int update_halt_gdb(struct target *target)
 {
+       struct target *gdb_target = NULL;
+       struct target_list *head;
+       struct target *curr;
        int retval = 0;
+
        if (target->gdb_service && target->gdb_service->core[0] == -1) {
                target->gdb_service->target = target;
                target->gdb_service->core[0] = target->coreid;
                retval += cortex_a_halt_smp(target);
        }
+
+       if (target->gdb_service)
+               gdb_target = target->gdb_service->target;
+
+       foreach_smp_target(head, target->head) {
+               curr = head->target;
+               /* skip calling context */
+               if (curr == target)
+                       continue;
+               if (!target_was_examined(curr))
+                       continue;
+               /* skip targets that were already halted */
+               if (curr->state == TARGET_HALTED)
+                       continue;
+               /* Skip gdb_target; it alerts GDB so has to be polled as last one */
+               if (curr == gdb_target)
+                       continue;
+
+               /* avoid recursion in cortex_a_poll() */
+               curr->smp = 0;
+               cortex_a_poll(curr);
+               curr->smp = 1;
+       }
+
+       /* after all targets were updated, poll the gdb serving target */
+       if (gdb_target != NULL && gdb_target != target)
+               cortex_a_poll(gdb_target);
        return retval;
 }
 
@@ -1002,7 +1011,7 @@ static int cortex_a_internal_restore(struct target *target, int current,
        arm->pc->valid = 1;
 
        /* restore dpm_mode at system halt */
-       dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
+       arm_dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
        /* called it now before restoring context because it uses cpu
         * register r0 for restoring cp15 control register */
        retval = cortex_a_restore_cp15_control_reg(target);
@@ -1149,10 +1158,8 @@ static int cortex_a_resume(struct target *target, int current,
 
 static int cortex_a_debug_entry(struct target *target)
 {
-       int i;
-       uint32_t regfile[16], cpsr, spsr, dscr;
+       uint32_t spsr, dscr;
        int retval = ERROR_OK;
-       struct working_area *regfile_working_area = NULL;
        struct cortex_a_common *cortex_a = target_to_cortex_a(target);
        struct armv7a_common *armv7a = target_to_armv7a(target);
        struct arm *arm = &armv7a->arm;
@@ -1193,56 +1200,10 @@ static int cortex_a_debug_entry(struct target *target)
                arm_dpm_report_wfar(&armv7a->dpm, wfar);
        }
 
-       /* REVISIT fast_reg_read is never set ... */
-
-       /* Examine target state and mode */
-       if (cortex_a->fast_reg_read)
-               target_alloc_working_area(target, 64, &regfile_working_area);
-
-
-       /* First load register acessible through core debug port*/
-       if (!regfile_working_area)
-               retval = arm_dpm_read_current_registers(&armv7a->dpm);
-       else {
-               retval = cortex_a_read_regs_through_mem(target,
-                               regfile_working_area->address, regfile);
-
-               target_free_working_area(target, regfile_working_area);
-               if (retval != ERROR_OK)
-                       return retval;
-
-               /* read Current PSR */
-               retval = cortex_a_dap_read_coreregister_u32(target, &cpsr, 16);
-               /*  store current cpsr */
-               if (retval != ERROR_OK)
-                       return retval;
-
-               LOG_DEBUG("cpsr: %8.8" PRIx32, cpsr);
-
-               arm_set_cpsr(arm, cpsr);
-
-               /* update cache */
-               for (i = 0; i <= ARM_PC; i++) {
-                       reg = arm_reg_current(arm, i);
-
-                       buf_set_u32(reg->value, 0, 32, regfile[i]);
-                       reg->valid = 1;
-                       reg->dirty = 0;
-               }
-
-               /* Fixup PC Resume Address */
-               if (cpsr & (1 << 5)) {
-                       /* T bit set for Thumb or ThumbEE state */
-                       regfile[ARM_PC] -= 4;
-               } else {
-                       /* ARM state */
-                       regfile[ARM_PC] -= 8;
-               }
-
-               reg = arm->pc;
-               buf_set_u32(reg->value, 0, 32, regfile[ARM_PC]);
-               reg->dirty = reg->valid;
-       }
+       /* First load register accessible through core debug port */
+       retval = arm_dpm_read_current_registers(&armv7a->dpm);
+       if (retval != ERROR_OK)
+               return retval;
 
        if (arm->spsr) {
                /* read Saved PSR */
@@ -1316,7 +1277,7 @@ static int cortex_a_post_debug_entry(struct target *target)
        cortex_a->curr_mode = armv7a->arm.core_mode;
 
        /* switch to SVC mode to read DACR */
-       dpm_modeswitch(&armv7a->dpm, ARM_MODE_SVC);
+       arm_dpm_modeswitch(&armv7a->dpm, ARM_MODE_SVC);
        armv7a->arm.mrc(target, 15,
                        0, 0, 3, 0,
                        &cortex_a->cp15_dacr_reg);
@@ -1324,7 +1285,7 @@ static int cortex_a_post_debug_entry(struct target *target)
        LOG_DEBUG("cp15_dacr_reg: %8.8" PRIx32,
                        cortex_a->cp15_dacr_reg);
 
-       dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
+       arm_dpm_modeswitch(&armv7a->dpm, ARM_MODE_ANY);
        return ERROR_OK;
 }
 
@@ -1386,6 +1347,7 @@ static int cortex_a_step(struct target *target, int current, target_addr_t addre
 
        /* Setup single step breakpoint */
        stepbreakpoint.address = address;
+       stepbreakpoint.asid = 0;
        stepbreakpoint.length = (arm->core_state == ARM_STATE_THUMB)
                ? 2 : 4;
        stepbreakpoint.type = BKPT_HARD;
@@ -2660,9 +2622,6 @@ static int cortex_a_read_phys_memory(struct target *target,
        target_addr_t address, uint32_t size,
        uint32_t count, uint8_t *buffer)
 {
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-       struct adiv5_dap *swjdp = armv7a->arm.dap;
-       uint8_t apsel = swjdp->apsel;
        int retval;
 
        if (!count || !buffer)
@@ -2671,9 +2630,6 @@ static int cortex_a_read_phys_memory(struct target *target,
        LOG_DEBUG("Reading memory at real address " TARGET_ADDR_FMT "; size %" PRId32 "; count %" PRId32,
                address, size, count);
 
-       if (armv7a->memory_ap_available && (apsel == armv7a->memory_ap->ap_num))
-               return mem_ap_read_buf(armv7a->memory_ap, buffer, size, count, address);
-
        /* read memory through the CPU */
        cortex_a_prep_memaccess(target, 1);
        retval = cortex_a_read_cpu_memory(target, address, size, count, buffer);
@@ -2698,57 +2654,10 @@ static int cortex_a_read_memory(struct target *target, target_addr_t address,
        return retval;
 }
 
-static int cortex_a_read_memory_ahb(struct target *target, target_addr_t address,
-       uint32_t size, uint32_t count, uint8_t *buffer)
-{
-       int mmu_enabled = 0;
-       target_addr_t virt, phys;
-       int retval;
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-       struct adiv5_dap *swjdp = armv7a->arm.dap;
-       uint8_t apsel = swjdp->apsel;
-
-       if (!armv7a->memory_ap_available || (apsel != armv7a->memory_ap->ap_num))
-               return target_read_memory(target, address, size, count, buffer);
-
-       /* cortex_a handles unaligned memory access */
-       LOG_DEBUG("Reading memory at address " TARGET_ADDR_FMT "; size %" PRId32 "; count %" PRId32,
-               address, size, count);
-
-       /* determine if MMU was enabled on target stop */
-       if (!armv7a->is_armv7r) {
-               retval = cortex_a_mmu(target, &mmu_enabled);
-               if (retval != ERROR_OK)
-                       return retval;
-       }
-
-       if (mmu_enabled) {
-               virt = address;
-               retval = cortex_a_virt2phys(target, virt, &phys);
-               if (retval != ERROR_OK)
-                       return retval;
-
-               LOG_DEBUG("Reading at virtual address. "
-                         "Translating v:" TARGET_ADDR_FMT " to r:" TARGET_ADDR_FMT,
-                         virt, phys);
-               address = phys;
-       }
-
-       if (!count || !buffer)
-               return ERROR_COMMAND_SYNTAX_ERROR;
-
-       retval = mem_ap_read_buf(armv7a->memory_ap, buffer, size, count, address);
-
-       return retval;
-}
-
 static int cortex_a_write_phys_memory(struct target *target,
        target_addr_t address, uint32_t size,
        uint32_t count, const uint8_t *buffer)
 {
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-       struct adiv5_dap *swjdp = armv7a->arm.dap;
-       uint8_t apsel = swjdp->apsel;
        int retval;
 
        if (!count || !buffer)
@@ -2757,9 +2666,6 @@ static int cortex_a_write_phys_memory(struct target *target,
        LOG_DEBUG("Writing memory to real address " TARGET_ADDR_FMT "; size %" PRId32 "; count %" PRId32,
                address, size, count);
 
-       if (armv7a->memory_ap_available && (apsel == armv7a->memory_ap->ap_num))
-               return mem_ap_write_buf(armv7a->memory_ap, buffer, size, count, address);
-
        /* write memory through the CPU */
        cortex_a_prep_memaccess(target, 1);
        retval = cortex_a_write_cpu_memory(target, address, size, count, buffer);
@@ -2786,51 +2692,6 @@ static int cortex_a_write_memory(struct target *target, target_addr_t address,
        return retval;
 }
 
-static int cortex_a_write_memory_ahb(struct target *target, target_addr_t address,
-       uint32_t size, uint32_t count, const uint8_t *buffer)
-{
-       int mmu_enabled = 0;
-       target_addr_t virt, phys;
-       int retval;
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-       struct adiv5_dap *swjdp = armv7a->arm.dap;
-       uint8_t apsel = swjdp->apsel;
-
-       if (!armv7a->memory_ap_available || (apsel != armv7a->memory_ap->ap_num))
-               return target_write_memory(target, address, size, count, buffer);
-
-       /* cortex_a handles unaligned memory access */
-       LOG_DEBUG("Writing memory at address " TARGET_ADDR_FMT "; size %" PRId32 "; count %" PRId32,
-               address, size, count);
-
-       /* determine if MMU was enabled on target stop */
-       if (!armv7a->is_armv7r) {
-               retval = cortex_a_mmu(target, &mmu_enabled);
-               if (retval != ERROR_OK)
-                       return retval;
-       }
-
-       if (mmu_enabled) {
-               virt = address;
-               retval = cortex_a_virt2phys(target, virt, &phys);
-               if (retval != ERROR_OK)
-                       return retval;
-
-               LOG_DEBUG("Writing to virtual address. "
-                         "Translating v:" TARGET_ADDR_FMT " to r:" TARGET_ADDR_FMT,
-                         virt,
-                         phys);
-               address = phys;
-       }
-
-       if (!count || !buffer)
-               return ERROR_COMMAND_SYNTAX_ERROR;
-
-       retval = mem_ap_write_buf(armv7a->memory_ap, buffer, size, count, address);
-
-       return retval;
-}
-
 static int cortex_a_read_buffer(struct target *target, target_addr_t address,
                                uint32_t count, uint8_t *buffer)
 {
@@ -2840,7 +2701,7 @@ static int cortex_a_read_buffer(struct target *target, target_addr_t address,
         * will have something to do with the size we leave to it. */
        for (size = 1; size < 4 && count >= size * 2 + (address & size); size *= 2) {
                if (address & size) {
-                       int retval = cortex_a_read_memory_ahb(target, address, size, 1, buffer);
+                       int retval = target_read_memory(target, address, size, 1, buffer);
                        if (retval != ERROR_OK)
                                return retval;
                        address += size;
@@ -2853,7 +2714,7 @@ static int cortex_a_read_buffer(struct target *target, target_addr_t address,
        for (; size > 0; size /= 2) {
                uint32_t aligned = count - count % size;
                if (aligned > 0) {
-                       int retval = cortex_a_read_memory_ahb(target, address, size, aligned / size, buffer);
+                       int retval = target_read_memory(target, address, size, aligned / size, buffer);
                        if (retval != ERROR_OK)
                                return retval;
                        address += aligned;
@@ -2874,7 +2735,7 @@ static int cortex_a_write_buffer(struct target *target, target_addr_t address,
         * will have something to do with the size we leave to it. */
        for (size = 1; size < 4 && count >= size * 2 + (address & size); size *= 2) {
                if (address & size) {
-                       int retval = cortex_a_write_memory_ahb(target, address, size, 1, buffer);
+                       int retval = target_write_memory(target, address, size, 1, buffer);
                        if (retval != ERROR_OK)
                                return retval;
                        address += size;
@@ -2887,7 +2748,7 @@ static int cortex_a_write_buffer(struct target *target, target_addr_t address,
        for (; size > 0; size /= 2) {
                uint32_t aligned = count - count % size;
                if (aligned > 0) {
-                       int retval = cortex_a_write_memory_ahb(target, address, size, aligned / size, buffer);
+                       int retval = target_write_memory(target, address, size, aligned / size, buffer);
                        if (retval != ERROR_OK)
                                return retval;
                        address += aligned;
@@ -2965,21 +2826,6 @@ static int cortex_a_examine_first(struct target *target)
 
        armv7a->debug_ap->memaccess_tck = 80;
 
-       /* Search for the AHB-AB.
-        * REVISIT: We should search for AXI-AP as well and make sure the AP's MEMTYPE says it
-        * can access system memory. */
-       armv7a->memory_ap_available = false;
-       retval = dap_find_ap(swjdp, AP_TYPE_AHB_AP, &armv7a->memory_ap);
-       if (retval == ERROR_OK) {
-               retval = mem_ap_init(armv7a->memory_ap);
-               if (retval == ERROR_OK)
-                       armv7a->memory_ap_available = true;
-       }
-       if (retval != ERROR_OK) {
-               /* AHB-AP not found or unavailable - use the CPU */
-               LOG_DEBUG("No AHB-AP available for memory access");
-       }
-
        if (!target->dbgbase_set) {
                uint32_t dbgbase;
                /* Get ROM Table base */
@@ -3139,8 +2985,6 @@ static int cortex_a_init_arch_info(struct target *target,
        cortex_a->common_magic = CORTEX_A_COMMON_MAGIC;
        armv7a->arm.dap = dap;
 
-       cortex_a->fast_reg_read = 0;
-
        /* register arch-specific functions */
        armv7a->examine_debug_reason = NULL;
 
@@ -3225,10 +3069,7 @@ static int cortex_a_mmu(struct target *target, int *enabled)
 static int cortex_a_virt2phys(struct target *target,
        target_addr_t virt, target_addr_t *phys)
 {
-       int retval = ERROR_FAIL;
-       struct armv7a_common *armv7a = target_to_armv7a(target);
-       struct adiv5_dap *swjdp = armv7a->arm.dap;
-       uint8_t apsel = swjdp->apsel;
+       int retval;
        int mmu_enabled = 0;
 
        /*
@@ -3243,23 +3084,12 @@ static int cortex_a_virt2phys(struct target *target,
                return ERROR_OK;
        }
 
-       if (armv7a->memory_ap_available && (apsel == armv7a->memory_ap->ap_num)) {
-               uint32_t ret;
-               retval = armv7a_mmu_translate_va(target,
-                               virt, &ret);
-               if (retval != ERROR_OK)
-                       goto done;
-               *phys = ret;
-       } else {/*  use this method if armv7a->memory_ap not selected
-                *  mmu must be enable in order to get a correct translation */
-               retval = cortex_a_mmu_modify(target, 1);
-               if (retval != ERROR_OK)
-                       goto done;
-               retval = armv7a_mmu_translate_va_pa(target, (uint32_t)virt,
+       /* mmu must be enable in order to get a correct translation */
+       retval = cortex_a_mmu_modify(target, 1);
+       if (retval != ERROR_OK)
+               return retval;
+       return armv7a_mmu_translate_va_pa(target, (uint32_t)virt,
                                                    (uint32_t *)phys, 1);
-       }
-done:
-       return retval;
 }
 
 COMMAND_HANDLER(cortex_a_handle_cache_info_command)
@@ -3438,7 +3268,7 @@ static const struct command_registration cortex_a_exec_command_handlers[] = {
        {
                .name = "dacrfixup",
                .handler = handle_cortex_a_dacrfixup_command,
-               .mode = COMMAND_EXEC,
+               .mode = COMMAND_ANY,
                .help = "set domain access control (DACR) to all-manager "
                        "on memory access",
                .usage = "['on'|'off']",