Georg Acher <acher@in.tum.de> - arm11 wip. run algorithm + small init bugfix.
git-svn-id: svn://svn.berlios.de/openocd/trunk@1023 b42882b7-edfa-0310-969c-e2dbd0fdcd60
This commit is contained in:
parent
ab362fb528
commit
3b2518bd73
|
@ -3,6 +3,8 @@
|
|||
* *
|
||||
* Copyright (C) 2008 Oyvind Harboe oyvind.harboe@zylin.com *
|
||||
* *
|
||||
* Copyright (C) 2008 Georg Acher <acher@in.tum.de> *
|
||||
* *
|
||||
* This program is free software; you can redistribute it and/or modify *
|
||||
* it under the terms of the GNU General Public License as published by *
|
||||
* the Free Software Foundation; either version 2 of the License, or *
|
||||
|
@ -1342,13 +1344,170 @@ int arm11_remove_watchpoint(struct target_s *target, watchpoint_t *watchpoint)
|
|||
return ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
// HACKHACKHACK - FIXME mode/state
|
||||
/* target algorithm support */
|
||||
int arm11_run_algorithm(struct target_s *target, int num_mem_params, mem_param_t *mem_params, int num_reg_params, reg_param_t *reg_param, u32 entry_point, u32 exit_point, int timeout_ms, void *arch_info)
|
||||
int arm11_run_algorithm(struct target_s *target, int num_mem_params, mem_param_t *mem_params,
|
||||
int num_reg_params, reg_param_t *reg_params, u32 entry_point, u32 exit_point,
|
||||
int timeout_ms, void *arch_info)
|
||||
{
|
||||
FNC_INFO_NOTIMPLEMENTED;
|
||||
arm11_common_t *arm11 = target->arch_info;
|
||||
armv4_5_algorithm_t *arm11_algorithm_info = arch_info;
|
||||
// enum armv4_5_state core_state = arm11->core_state;
|
||||
// enum armv4_5_mode core_mode = arm11->core_mode;
|
||||
u32 context[16];
|
||||
u32 cpsr;
|
||||
int exit_breakpoint_size = 0;
|
||||
int i;
|
||||
int retval = ERROR_OK;
|
||||
LOG_DEBUG("Running algorithm");
|
||||
|
||||
return ERROR_OK;
|
||||
if (arm11_algorithm_info->common_magic != ARMV4_5_COMMON_MAGIC)
|
||||
{
|
||||
LOG_ERROR("current target isn't an ARMV4/5 target");
|
||||
return ERROR_TARGET_INVALID;
|
||||
}
|
||||
|
||||
if (target->state != TARGET_HALTED)
|
||||
{
|
||||
LOG_WARNING("target not halted");
|
||||
return ERROR_TARGET_NOT_HALTED;
|
||||
}
|
||||
|
||||
// FIXME
|
||||
// if (armv4_5_mode_to_number(arm11->core_mode)==-1)
|
||||
// return ERROR_FAIL;
|
||||
|
||||
// Save regs
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
context[i] = buf_get_u32((u8*)(&arm11->reg_values[i]),0,32);
|
||||
LOG_DEBUG("Save %i: 0x%x",i,context[i]);
|
||||
}
|
||||
|
||||
cpsr = buf_get_u32((u8*)(arm11->reg_values+ARM11_RC_CPSR),0,32);
|
||||
LOG_DEBUG("Save CPSR: 0x%x",i,cpsr);
|
||||
|
||||
for (i = 0; i < num_mem_params; i++)
|
||||
{
|
||||
target_write_buffer(target, mem_params[i].address, mem_params[i].size, mem_params[i].value);
|
||||
}
|
||||
|
||||
// Set register parameters
|
||||
for (i = 0; i < num_reg_params; i++)
|
||||
{
|
||||
reg_t *reg = register_get_by_name(arm11->core_cache, reg_params[i].reg_name, 0);
|
||||
u32 val;
|
||||
if (!reg)
|
||||
{
|
||||
LOG_ERROR("BUG: register '%s' not found", reg_params[i].reg_name);
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
if (reg->size != reg_params[i].size)
|
||||
{
|
||||
LOG_ERROR("BUG: register '%s' size doesn't match reg_params[i].size", reg_params[i].reg_name);
|
||||
exit(-1);
|
||||
}
|
||||
arm11_set_reg(reg,reg_params[i].value);
|
||||
// printf("%i: Set %s =%08x\n", i, reg_params[i].reg_name,val);
|
||||
}
|
||||
|
||||
exit_breakpoint_size = 4;
|
||||
|
||||
/* arm11->core_state = arm11_algorithm_info->core_state;
|
||||
if (arm11->core_state == ARMV4_5_STATE_ARM)
|
||||
exit_breakpoint_size = 4;
|
||||
else if (arm11->core_state == ARMV4_5_STATE_THUMB)
|
||||
exit_breakpoint_size = 2;
|
||||
else
|
||||
{
|
||||
LOG_ERROR("BUG: can't execute algorithms when not in ARM or Thumb state");
|
||||
exit(-1);
|
||||
}
|
||||
*/
|
||||
if (arm11_algorithm_info->core_mode != ARMV4_5_MODE_ANY)
|
||||
{
|
||||
LOG_DEBUG("setting core_mode: 0x%2.2x", arm11_algorithm_info->core_mode);
|
||||
buf_set_u32(arm11->reg_list[ARM11_RC_CPSR].value, 0, 5, arm11_algorithm_info->core_mode);
|
||||
arm11->reg_list[ARM11_RC_CPSR].dirty = 1;
|
||||
arm11->reg_list[ARM11_RC_CPSR].valid = 1;
|
||||
}
|
||||
|
||||
if ((retval = breakpoint_add(target, exit_point, exit_breakpoint_size, BKPT_HARD)) != ERROR_OK)
|
||||
{
|
||||
LOG_ERROR("can't add breakpoint to finish algorithm execution");
|
||||
retval = ERROR_TARGET_FAILURE;
|
||||
goto restore;
|
||||
}
|
||||
|
||||
target_resume(target, 0, entry_point, 1, 0); // no debug, otherwise breakpoint is not set
|
||||
|
||||
target_wait_state(target, TARGET_HALTED, timeout_ms);
|
||||
if (target->state != TARGET_HALTED)
|
||||
{
|
||||
if ((retval=target_halt(target))!=ERROR_OK)
|
||||
return retval;
|
||||
if ((retval=target_wait_state(target, TARGET_HALTED, 500))!=ERROR_OK)
|
||||
{
|
||||
return retval;
|
||||
}
|
||||
retval = ERROR_TARGET_TIMEOUT;
|
||||
goto del_breakpoint;
|
||||
}
|
||||
|
||||
if (buf_get_u32(arm11->reg_list[15].value, 0, 32) != exit_point)
|
||||
{
|
||||
LOG_WARNING("target reentered debug state, but not at the desired exit point: 0x%4.4x",
|
||||
buf_get_u32(arm11->reg_list[15].value, 0, 32));
|
||||
retval = ERROR_TARGET_TIMEOUT;
|
||||
goto del_breakpoint;
|
||||
}
|
||||
|
||||
for (i = 0; i < num_mem_params; i++)
|
||||
{
|
||||
if (mem_params[i].direction != PARAM_OUT)
|
||||
target_read_buffer(target, mem_params[i].address, mem_params[i].size, mem_params[i].value);
|
||||
}
|
||||
|
||||
for (i = 0; i < num_reg_params; i++)
|
||||
{
|
||||
if (reg_params[i].direction != PARAM_OUT)
|
||||
{
|
||||
reg_t *reg = register_get_by_name(arm11->core_cache, reg_params[i].reg_name, 0);
|
||||
if (!reg)
|
||||
{
|
||||
LOG_ERROR("BUG: register '%s' not found", reg_params[i].reg_name);
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
if (reg->size != reg_params[i].size)
|
||||
{
|
||||
LOG_ERROR("BUG: register '%s' size doesn't match reg_params[i].size", reg_params[i].reg_name);
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
buf_set_u32(reg_params[i].value, 0, 32, buf_get_u32(reg->value, 0, 32));
|
||||
}
|
||||
}
|
||||
|
||||
del_breakpoint:
|
||||
breakpoint_remove(target, exit_point);
|
||||
|
||||
restore:
|
||||
// Restore context
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
LOG_DEBUG("restoring register %s with value 0x%8.8x",
|
||||
arm11->reg_list[i].name, context[i]);
|
||||
arm11_set_reg(&arm11->reg_list[i], &context[i]);
|
||||
}
|
||||
LOG_DEBUG("restoring CPSR with value 0x%8.8x", cpsr);
|
||||
arm11_set_reg(&arm11->reg_list[ARM11_RC_CPSR], &cpsr);
|
||||
|
||||
// arm11->core_state = core_state;
|
||||
// arm11->core_mode = core_mode;
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
int arm11_target_create(struct target_s *target, Jim_Interp *interp)
|
||||
|
@ -1537,7 +1696,7 @@ void arm11_build_reg_cache(target_t *target)
|
|||
reg_cache_t **cache_p = register_get_last_cache_p(&target->reg_cache);
|
||||
(*cache_p) = cache;
|
||||
|
||||
// armv7m->core_cache = cache;
|
||||
arm11->core_cache = cache;
|
||||
// armv7m->process_context = cache;
|
||||
|
||||
size_t i;
|
||||
|
@ -1670,7 +1829,7 @@ arm11_common_t * arm11_find_target(const char * arg)
|
|||
{target_t * t;
|
||||
for (t = all_targets; t; t = t->next)
|
||||
{
|
||||
if (t->type != &arm11_target)
|
||||
if (strcmp(t->type->name,"arm11"))
|
||||
continue;
|
||||
|
||||
arm11_common_t * arm11 = t->arch_info;
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
/***************************************************************************
|
||||
* Copyright (C) 2008 digenius technology GmbH. *
|
||||
* *
|
||||
* Copyright (C) 2008 Georg Acher <acher@in.tum.de> *
|
||||
* *
|
||||
* This program is free software; you can redistribute it and/or modify *
|
||||
* it under the terms of the GNU General Public License as published by *
|
||||
* the Free Software Foundation; either version 2 of the License, or *
|
||||
|
@ -107,6 +109,8 @@ typedef struct arm11_common_s
|
|||
size_t free_brps; /**< keep track of breakpoints allocated by arm11_add_breakpoint() */
|
||||
size_t free_wrps; /**< keep track of breakpoints allocated by arm11_add_watchpoint() */
|
||||
|
||||
// GA
|
||||
reg_cache_t *core_cache;
|
||||
} arm11_common_t;
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue