Fix memory access on some targets. (#428)

Fix memory access on 64-bit targets with no progbuf and sba that
supports 32-bit accesses but not 64-bit accesses. Bug was introduced in #419.

This fixes https://github.com/riscv/riscv-tests/issues/217.

Change-Id: Ib5ddf9886b77e3d58fe1d891b560ad03d5a46da1
busy
Tim Newsome 2019-11-22 11:37:46 -08:00 committed by GitHub
parent 739d16d503
commit de00906ebd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 37 additions and 4 deletions

View File

@ -1727,6 +1727,29 @@ static int riscv013_hart_count(struct target *target)
return dm->hart_count; return dm->hart_count;
} }
static unsigned riscv013_data_bits(struct target *target)
{
RISCV013_INFO(info);
/* TODO: Once there is a spec for discovering abstract commands, we can
* take those into account as well. For now we assume abstract commands
* support XLEN-wide accesses. */
if (info->progbufsize >= 2 && !riscv_prefer_sba)
return riscv_xlen(target);
if (get_field(info->sbcs, DMI_SBCS_SBACCESS128))
return 128;
if (get_field(info->sbcs, DMI_SBCS_SBACCESS64))
return 64;
if (get_field(info->sbcs, DMI_SBCS_SBACCESS32))
return 32;
if (get_field(info->sbcs, DMI_SBCS_SBACCESS16))
return 16;
if (get_field(info->sbcs, DMI_SBCS_SBACCESS8))
return 8;
return riscv_xlen(target);
}
static int init_target(struct command_context *cmd_ctx, static int init_target(struct command_context *cmd_ctx,
struct target *target) struct target *target)
{ {
@ -1759,6 +1782,7 @@ static int init_target(struct command_context *cmd_ctx,
generic_info->test_sba_config_reg = &riscv013_test_sba_config_reg; generic_info->test_sba_config_reg = &riscv013_test_sba_config_reg;
generic_info->test_compliance = &riscv013_test_compliance; generic_info->test_compliance = &riscv013_test_compliance;
generic_info->hart_count = &riscv013_hart_count; generic_info->hart_count = &riscv013_hart_count;
generic_info->data_bits = &riscv013_data_bits;
generic_info->version_specific = calloc(1, sizeof(riscv013_info_t)); generic_info->version_specific = calloc(1, sizeof(riscv013_info_t));
if (!generic_info->version_specific) if (!generic_info->version_specific)
return ERROR_FAIL; return ERROR_FAIL;

View File

@ -2462,6 +2462,14 @@ static unsigned riscv_xlen_nonconst(struct target *target)
return riscv_xlen(target); return riscv_xlen(target);
} }
static unsigned riscv_data_bits(struct target *target)
{
RISCV_INFO(r);
if (r->data_bits)
return r->data_bits(target);
return riscv_xlen(target);
}
struct target_type riscv_target = { struct target_type riscv_target = {
.name = "riscv", .name = "riscv",
@ -2501,7 +2509,7 @@ struct target_type riscv_target = {
.commands = riscv_command_handlers, .commands = riscv_command_handlers,
.address_bits = riscv_xlen_nonconst, .address_bits = riscv_xlen_nonconst,
.data_bits = riscv_xlen_nonconst .data_bits = riscv_data_bits
}; };
/*** RISC-V Interface ***/ /*** RISC-V Interface ***/

View File

@ -146,6 +146,7 @@ typedef struct {
/* How many harts are attached to the DM that this target is attached to? */ /* How many harts are attached to the DM that this target is attached to? */
int (*hart_count)(struct target *target); int (*hart_count)(struct target *target);
unsigned (*data_bits)(struct target *target);
} riscv_info_t; } riscv_info_t;
typedef struct { typedef struct {

View File

@ -297,9 +297,9 @@ struct target_type {
* implemented, it's assumed to be 32. */ * implemented, it's assumed to be 32. */
unsigned (*address_bits)(struct target *target); unsigned (*address_bits)(struct target *target);
/* Return the number of data bits this target supports. This will /* Return the number of system bus data bits this target supports. This
* typically be 32 for 32-bit targets, and 64 for 64-bit targets. If not * will typically be 32 for 32-bit targets, and 64 for 64-bit targets. If
* implemented, it's assumed to be 32. */ * not implemented, it's assumed to be 32. */
unsigned (*data_bits)(struct target *target); unsigned (*data_bits)(struct target *target);
}; };