ARM: use arm_reg_current()

Start using the arm_reg_current() call.  This shrinks and speeds
the affected code.  It can also prevent some coredumps coming from
invalid CPSR values ... the ARMV4_5_CORE_REG_MODE() macro returns
bogus registers if e.g. "Secure Monitor" mode isn't supported by
the current CPU.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
__archive__
David Brownell 2009-11-22 10:21:48 -08:00
parent fa618cc74d
commit b404b9ab57
3 changed files with 74 additions and 61 deletions

View File

@ -1245,9 +1245,11 @@ int arm7_9_soft_reset_halt(struct target *target)
/* reset registers */ /* reset registers */
for (i = 0; i <= 14; i++) for (i = 0; i <= 14; i++)
{ {
buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).value, 0, 32, 0xffffffff); struct reg *r = arm_reg_current(armv4_5, i);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).dirty = 1;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).valid = 1; buf_set_u32(r->value, 0, 32, 0xffffffff);
r->dirty = 1;
r->valid = 1;
} }
if ((retval = target_call_event_callbacks(target, TARGET_EVENT_HALTED)) != ERROR_OK) if ((retval = target_call_event_callbacks(target, TARGET_EVENT_HALTED)) != ERROR_OK)
@ -1443,32 +1445,31 @@ static int arm7_9_debug_entry(struct target *target)
for (i = 0; i <= 15; i++) for (i = 0; i <= 15; i++)
{ {
struct reg *r = arm_reg_current(armv4_5, i);
LOG_DEBUG("r%i: 0x%8.8" PRIx32 "", i, context[i]); LOG_DEBUG("r%i: 0x%8.8" PRIx32 "", i, context[i]);
buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).value, 0, 32, context[i]);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).dirty = 0; buf_set_u32(r->value, 0, 32, context[i]);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).valid = 1; /* r0 and r15 (pc) have to be restored later */
r->dirty = (i == 0) || (i == 15);
r->valid = 1;
} }
LOG_DEBUG("entered debug state at PC 0x%" PRIx32 "", context[15]); LOG_DEBUG("entered debug state at PC 0x%" PRIx32 "", context[15]);
/* exceptions other than USR & SYS have a saved program status register */ /* exceptions other than USR & SYS have a saved program status register */
if ((armv4_5->core_mode != ARMV4_5_MODE_USR) && (armv4_5->core_mode != ARMV4_5_MODE_SYS)) if (armv4_5->spsr) {
{
uint32_t spsr; uint32_t spsr;
arm7_9->read_xpsr(target, &spsr, 1); arm7_9->read_xpsr(target, &spsr, 1);
if ((retval = jtag_execute_queue()) != ERROR_OK) if ((retval = jtag_execute_queue()) != ERROR_OK)
{ {
return retval; return retval;
} }
buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).value, 0, 32, spsr); buf_set_u32(armv4_5->spsr->value, 0, 32, spsr);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).dirty = 0; armv4_5->spsr->dirty = 0;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 16).valid = 1; armv4_5->spsr->valid = 1;
} }
/* r0 and r15 (pc) have to be restored later */
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 15).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 15).valid;
if ((retval = jtag_execute_queue()) != ERROR_OK) if ((retval = jtag_execute_queue()) != ERROR_OK)
return retval; return retval;
@ -2377,8 +2378,11 @@ int arm7_9_read_memory(struct target *target, uint32_t address, uint32_t size, u
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
for (i = 0; i <= last_reg; i++) for (i = 0; i <= last_reg; i++) {
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).valid; struct reg *r = arm_reg_current(armv4_5, i);
r->dirty = r->valid;
}
arm7_9->read_xpsr(target, &cpsr, 0); arm7_9->read_xpsr(target, &cpsr, 0);
if ((retval = jtag_execute_queue()) != ERROR_OK) if ((retval = jtag_execute_queue()) != ERROR_OK)
@ -2562,8 +2566,11 @@ int arm7_9_write_memory(struct target *target, uint32_t address, uint32_t size,
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
for (i = 0; i <= last_reg; i++) for (i = 0; i <= last_reg; i++) {
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, i).valid; struct reg *r = arm_reg_current(armv4_5, i);
r->dirty = r->valid;
}
arm7_9->read_xpsr(target, &cpsr, 0); arm7_9->read_xpsr(target, &cpsr, 0);
if ((retval = jtag_execute_queue()) != ERROR_OK) if ((retval = jtag_execute_queue()) != ERROR_OK)

View File

@ -216,6 +216,7 @@ static int arm920t_read_cp15_interpreted(struct target *target,
uint32_t* regs_p[1]; uint32_t* regs_p[1];
uint32_t regs[2]; uint32_t regs[2];
uint32_t cp15c15 = 0x0; uint32_t cp15c15 = 0x0;
struct reg *r = armv4_5->core_cache->reg_list;
/* load address into R1 */ /* load address into R1 */
regs[1] = address; regs[1] = address;
@ -247,8 +248,8 @@ static int arm920t_read_cp15_interpreted(struct target *target,
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).dirty = 1; r[0].dirty = 1;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).dirty = 1; r[1].dirty = 1;
return ERROR_OK; return ERROR_OK;
} }
@ -260,6 +261,7 @@ int arm920t_write_cp15_interpreted(struct target *target,
uint32_t cp15c15 = 0x0; uint32_t cp15c15 = 0x0;
struct arm *armv4_5 = target_to_armv4_5(target); struct arm *armv4_5 = target_to_armv4_5(target);
uint32_t regs[2]; uint32_t regs[2];
struct reg *r = armv4_5->core_cache->reg_list;
/* load value, address into R0, R1 */ /* load value, address into R0, R1 */
regs[0] = value; regs[0] = value;
@ -287,8 +289,8 @@ int arm920t_write_cp15_interpreted(struct target *target,
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).dirty = 1; r[0].dirty = 1;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).dirty = 1; r[1].dirty = 1;
return ERROR_OK; return ERROR_OK;
} }
@ -678,6 +680,7 @@ COMMAND_HANDLER(arm920t_handle_read_cache_command)
FILE *output; FILE *output;
struct arm920t_cache_line d_cache[8][64], i_cache[8][64]; struct arm920t_cache_line d_cache[8][64], i_cache[8][64];
int segment, index; int segment, index;
struct reg *r;
retval = arm920t_verify_pointer(CMD_CTX, arm920t); retval = arm920t_verify_pointer(CMD_CTX, arm920t);
if (retval != ERROR_OK) if (retval != ERROR_OK)
@ -893,17 +896,22 @@ COMMAND_HANDLER(arm920t_handle_read_cache_command)
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
/* mark registers dirty. */ /* force writeback of the valid data */
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).valid; r = armv4_5->core_cache->reg_list;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).valid; r[0].dirty = r[0].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 2).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 2).valid; r[1].dirty = r[1].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 3).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 3).valid; r[2].dirty = r[2].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 4).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 4).valid; r[3].dirty = r[3].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 5).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 5).valid; r[4].dirty = r[4].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 6).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 6).valid; r[5].dirty = r[5].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 7).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 7).valid; r[6].dirty = r[6].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 8).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 8).valid; r[7].dirty = r[7].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 9).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 9).valid;
r = arm_reg_current(armv4_5, 8);
r->dirty = r->valid;
r = arm_reg_current(armv4_5, 9);
r->dirty = r->valid;
return ERROR_OK; return ERROR_OK;
} }
@ -924,6 +932,7 @@ COMMAND_HANDLER(arm920t_handle_read_mmu_command)
uint32_t Dlockdown, Ilockdown; uint32_t Dlockdown, Ilockdown;
struct arm920t_tlb_entry d_tlb[64], i_tlb[64]; struct arm920t_tlb_entry d_tlb[64], i_tlb[64];
int victim; int victim;
struct reg *r;
retval = arm920t_verify_pointer(CMD_CTX, arm920t); retval = arm920t_verify_pointer(CMD_CTX, arm920t);
if (retval != ERROR_OK) if (retval != ERROR_OK)
@ -1176,17 +1185,22 @@ COMMAND_HANDLER(arm920t_handle_read_mmu_command)
if (!is_arm_mode(armv4_5->core_mode)) if (!is_arm_mode(armv4_5->core_mode))
return ERROR_FAIL; return ERROR_FAIL;
/* mark registers dirty */ /* force writeback of the valid data */
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0).valid; r = armv4_5->core_cache->reg_list;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 1).valid; r[0].dirty = r[0].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 2).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 2).valid; r[1].dirty = r[1].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 3).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 3).valid; r[2].dirty = r[2].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 4).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 4).valid; r[3].dirty = r[3].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 5).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 5).valid; r[4].dirty = r[4].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 6).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 6).valid; r[5].dirty = r[5].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 7).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 7).valid; r[6].dirty = r[6].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 8).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 8).valid; r[7].dirty = r[7].valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 9).dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 9).valid;
r = arm_reg_current(armv4_5, 8);
r->dirty = r->valid;
r = arm_reg_current(armv4_5, 9);
r->dirty = r->valid;
return ERROR_OK; return ERROR_OK;
} }

View File

@ -496,8 +496,7 @@ static int cortex_a8_resume(struct target *target, int current,
/* current = 1: continue on current pc, otherwise continue at <address> */ /* current = 1: continue on current pc, otherwise continue at <address> */
resume_pc = buf_get_u32( resume_pc = buf_get_u32(
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_cache->reg_list[15].value,
armv4_5->core_mode, 15).value,
0, 32); 0, 32);
if (!current) if (!current)
resume_pc = address; resume_pc = address;
@ -522,13 +521,10 @@ static int cortex_a8_resume(struct target *target, int current,
return ERROR_FAIL; return ERROR_FAIL;
} }
LOG_DEBUG("resume pc = 0x%08" PRIx32, resume_pc); LOG_DEBUG("resume pc = 0x%08" PRIx32, resume_pc);
buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, buf_set_u32(armv4_5->core_cache->reg_list[15].value,
armv4_5->core_mode, 15).value,
0, 32, resume_pc); 0, 32, resume_pc);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_cache->reg_list[15].dirty = 1;
armv4_5->core_mode, 15).dirty = 1; armv4_5->core_cache->reg_list[15].valid = 1;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache,
armv4_5->core_mode, 15).valid = 1;
cortex_a8_restore_context(target); cortex_a8_restore_context(target);
@ -653,8 +649,7 @@ static int cortex_a8_debug_entry(struct target *target)
/* update cache */ /* update cache */
for (i = 0; i <= ARM_PC; i++) for (i = 0; i <= ARM_PC; i++)
{ {
reg = &ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, reg = arm_reg_current(armv4_5, i);
armv4_5->core_mode, i);
buf_set_u32(reg->value, 0, 32, regfile[i]); buf_set_u32(reg->value, 0, 32, regfile[i]);
reg->valid = 1; reg->valid = 1;
@ -672,13 +667,10 @@ static int cortex_a8_debug_entry(struct target *target)
// ARM state // ARM state
regfile[ARM_PC] -= 8; regfile[ARM_PC] -= 8;
} }
buf_set_u32(ARMV4_5_CORE_REG_MODE(armv4_5->core_cache,
armv4_5->core_mode, ARM_PC).value,
0, 32, regfile[ARM_PC]);
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 0) reg = armv4_5->core_cache->reg_list + 15;
.dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, buf_set_u32(reg->value, 0, 32, regfile[ARM_PC]);
armv4_5->core_mode, 0).valid; reg->dirty = reg->valid;
ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 15) ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, armv4_5->core_mode, 15)
.dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache, .dirty = ARMV4_5_CORE_REG_MODE(armv4_5->core_cache,
armv4_5->core_mode, 15).valid; armv4_5->core_mode, 15).valid;