Fix a buffer overflow
This commit is contained in:
parent
98df29b8d1
commit
22d102e3c1
|
@ -15,11 +15,11 @@ riscv_addr_t riscv_program_gal(struct riscv_program *p, riscv_addr_t addr);
|
|||
int riscv_program_lah(struct riscv_program *p, enum gdb_regno d, riscv_addr_t addr);
|
||||
int riscv_program_lal(struct riscv_program *p, enum gdb_regno d, riscv_addr_t addr);
|
||||
|
||||
int riscv_program_insert(struct riscv_program *p, riscv_insn_t i);
|
||||
|
||||
/* Program interface. */
|
||||
int riscv_program_init(struct riscv_program *p, struct target *target)
|
||||
{
|
||||
LOG_DEBUG("riscv_program_init: p=0x%016lx", p);
|
||||
|
||||
memset(p, 0, sizeof(*p));
|
||||
p->target = target;
|
||||
p->instruction_count = 0;
|
||||
|
@ -59,11 +59,17 @@ int riscv_program_exec(struct riscv_program *p, struct target *t)
|
|||
|
||||
if (p->writes_memory && (riscv_program_fence(p) != ERROR_OK)) {
|
||||
LOG_ERROR("Unable to write fence");
|
||||
for(size_t i = 0; i < riscv_debug_buffer_size(p->target); ++i)
|
||||
LOG_ERROR("ram[%02x]: DASM(0x%08lx) [0x%08lx]", i, p->debug_buffer[i], p->debug_buffer[i]);
|
||||
abort();
|
||||
return ERROR_FAIL;
|
||||
}
|
||||
|
||||
if (riscv_program_ebreak(p) != ERROR_OK) {
|
||||
LOG_ERROR("Unable to write ebreak");
|
||||
for(size_t i = 0; i < riscv_debug_buffer_size(p->target); ++i)
|
||||
LOG_ERROR("ram[%02x]: DASM(0x%08lx) [0x%08lx]", i, p->debug_buffer[i], p->debug_buffer[i]);
|
||||
abort();
|
||||
return ERROR_FAIL;
|
||||
}
|
||||
|
||||
|
@ -145,9 +151,9 @@ riscv_insn_t riscv_program_read_ram(struct riscv_program *p, riscv_addr_t addr)
|
|||
void riscv_program_write_ram(struct riscv_program *p, riscv_addr_t addr, uint64_t d)
|
||||
{
|
||||
if (addr < riscv_debug_buffer_addr(p->target))
|
||||
return -1;
|
||||
return;
|
||||
if (addr > riscv_debug_buffer_addr(p->target) + (riscv_debug_buffer_size(p->target) * sizeof(p->debug_buffer[0])))
|
||||
return -1;
|
||||
return;
|
||||
|
||||
int off = (addr - riscv_debug_buffer_addr(p->target)) / sizeof(p->debug_buffer[0]);
|
||||
p->debug_buffer[off] = d;
|
||||
|
@ -329,12 +335,14 @@ int riscv_program_dont_restore_register(struct riscv_program *p, enum gdb_regno
|
|||
{
|
||||
assert(r < RISCV_REGISTER_COUNT);
|
||||
p->writes_xreg[r] = 0;
|
||||
return ERROR_OK;
|
||||
}
|
||||
|
||||
int riscv_program_do_restore_register(struct riscv_program *p, enum gdb_regno r)
|
||||
{
|
||||
assert(r < RISCV_REGISTER_COUNT);
|
||||
p->writes_xreg[r] = 1;
|
||||
return ERROR_OK;
|
||||
}
|
||||
|
||||
void riscv_program_reserve_register(struct riscv_program *p, enum gdb_regno r)
|
||||
|
@ -393,10 +401,18 @@ int riscv_program_lal(struct riscv_program *p, enum gdb_regno d, riscv_addr_t ad
|
|||
|
||||
int riscv_program_insert(struct riscv_program *p, riscv_insn_t i)
|
||||
{
|
||||
if (p->instruction_count + p->data_count + 1 > riscv_debug_buffer_size(p->target))
|
||||
LOG_DEBUG("instruction_count: %d (p=0x%016lx)", p->instruction_count, p);
|
||||
|
||||
if (p->instruction_count + p->data_count + 1 > riscv_debug_buffer_size(p->target)) {
|
||||
LOG_DEBUG("Unable to insert instruction:");
|
||||
LOG_DEBUG(" instruction_count=%d", p->instruction_count);
|
||||
LOG_DEBUG(" data_count =%d", p->data_count);
|
||||
LOG_DEBUG(" buffer size =%d", riscv_debug_buffer_size(p->target));
|
||||
return ERROR_FAIL;
|
||||
}
|
||||
|
||||
LOG_DEBUG("PROGBUF[%d] = DASM(0x%08x) [0x%08x]", p->instruction_count, i, i);
|
||||
p->debug_buffer[p->instruction_count] = i;
|
||||
p->instruction_count++;
|
||||
return ERROR_OK;
|
||||
}
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
#include "riscv.h"
|
||||
|
||||
#define RISCV_MAX_DEBUG_BUFFER_SIZE 16
|
||||
#define RISCV_MAX_DEBUG_BUFFER_SIZE 32
|
||||
#define RISCV_REGISTER_COUNT 32
|
||||
#define RISCV_DSCRATCH_COUNT 2
|
||||
|
||||
|
|
|
@ -569,6 +569,10 @@ static int register_write_direct(struct target *target, unsigned number,
|
|||
riscv_program_write_ram(&program, input + 4, value >> 32);
|
||||
case 32:
|
||||
riscv_program_write_ram(&program, input, value);
|
||||
break;
|
||||
default:
|
||||
LOG_ERROR("Unknown XLEN: %d\n", riscv_xlen(target));
|
||||
abort();
|
||||
}
|
||||
|
||||
if (number >= GDB_REGNO_XPR0 && number <= GDB_REGNO_XPR31) {
|
||||
|
@ -1132,6 +1136,9 @@ static int examine(struct target *target)
|
|||
* program buffer. */
|
||||
r->debug_buffer_size[i] = riscv013_progbuf_size(target);
|
||||
|
||||
/* Guess this is a 32-bit system, we're probing it. */
|
||||
r->xlen[i] = 32;
|
||||
|
||||
/* First find the low 32 bits of the program buffer. This is
|
||||
* used to check for alignment. */
|
||||
struct riscv_program program32;
|
||||
|
@ -1149,7 +1156,6 @@ static int examine(struct target *target)
|
|||
r->xlen[i] = -1;
|
||||
continue;
|
||||
}
|
||||
r->xlen[i] = 32;
|
||||
r->debug_buffer_addr[i] = progbuf_addr;
|
||||
|
||||
/* Check to see if the core can execute 64 bit instructions.
|
||||
|
|
|
@ -767,10 +767,7 @@ void riscv_info_init(riscv_info_t *r)
|
|||
r->rtos_enabled = true;
|
||||
|
||||
for (size_t h = 0; h < RISCV_MAX_HARTS; ++h) {
|
||||
/* FIXME: I need to rip out Tim's probing sequence, as it
|
||||
* disrupts the running code. For now, I'm just hard-coding
|
||||
* XLEN to 64 for all cores at reset. */
|
||||
r->xlen[h] = 64;
|
||||
r->xlen[h] = -1;
|
||||
r->hart_state[h] = RISCV_HART_UNKNOWN;
|
||||
r->debug_buffer_addr[h] = -1;
|
||||
|
||||
|
@ -904,11 +901,16 @@ bool riscv_rtos_enabled(const struct target *target)
|
|||
void riscv_set_current_hartid(struct target *target, int hartid)
|
||||
{
|
||||
RISCV_INFO(r);
|
||||
register_cache_invalidate(target->reg_cache);
|
||||
r->current_hartid = hartid;
|
||||
r->select_current_hart(target);
|
||||
|
||||
/* This might get called during init, in which case we shouldn't be
|
||||
* setting up the register cache. */
|
||||
if (!target_was_examined(target))
|
||||
return;
|
||||
|
||||
/* Update the register list's widths. */
|
||||
register_cache_invalidate(target->reg_cache);
|
||||
for (size_t i = 0; i < GDB_REGNO_COUNT; ++i) {
|
||||
struct reg *reg = &target->reg_cache->reg_list[i];
|
||||
|
||||
|
|
Loading…
Reference in New Issue