Ask the RTOS which target to set swbp on. (#673)
This lets the RTOS pick the "current" target, which matters if address translation differs between threads. Change-Id: I5b5510ab6a06621589c902f42a91562055817dc4 Signed-off-by: Tim Newsome <tim@sifive.com>
This commit is contained in:
parent
6f3daf38c7
commit
52ca5d198e
|
@ -43,6 +43,8 @@ static int hwthread_read_buffer(struct rtos *rtos, target_addr_t address,
|
||||||
uint32_t size, uint8_t *buffer);
|
uint32_t size, uint8_t *buffer);
|
||||||
static int hwthread_write_buffer(struct rtos *rtos, target_addr_t address,
|
static int hwthread_write_buffer(struct rtos *rtos, target_addr_t address,
|
||||||
uint32_t size, const uint8_t *buffer);
|
uint32_t size, const uint8_t *buffer);
|
||||||
|
struct target *hwthread_swbp_target(struct rtos *rtos, target_addr_t address,
|
||||||
|
uint32_t length, enum breakpoint_type type);
|
||||||
|
|
||||||
#define HW_THREAD_NAME_STR_SIZE (32)
|
#define HW_THREAD_NAME_STR_SIZE (32)
|
||||||
|
|
||||||
|
@ -66,6 +68,7 @@ const struct rtos_type hwthread_rtos = {
|
||||||
.needs_fake_step = hwthread_needs_fake_step,
|
.needs_fake_step = hwthread_needs_fake_step,
|
||||||
.read_buffer = hwthread_read_buffer,
|
.read_buffer = hwthread_read_buffer,
|
||||||
.write_buffer = hwthread_write_buffer,
|
.write_buffer = hwthread_write_buffer,
|
||||||
|
.swbp_target = hwthread_swbp_target
|
||||||
};
|
};
|
||||||
|
|
||||||
struct hwthread_params {
|
struct hwthread_params {
|
||||||
|
@ -444,3 +447,9 @@ static int hwthread_write_buffer(struct rtos *rtos, target_addr_t address,
|
||||||
|
|
||||||
return target_write_buffer(curr, address, size, buffer);
|
return target_write_buffer(curr, address, size, buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct target *hwthread_swbp_target(struct rtos *rtos, target_addr_t address,
|
||||||
|
uint32_t length, enum breakpoint_type type)
|
||||||
|
{
|
||||||
|
return hwthread_find_thread(rtos->target, rtos->current_thread);
|
||||||
|
}
|
||||||
|
|
|
@ -836,3 +836,11 @@ int rtos_write_buffer(struct target *target, target_addr_t address,
|
||||||
return target->rtos->type->write_buffer(target->rtos, address, size, buffer);
|
return target->rtos->type->write_buffer(target->rtos, address, size, buffer);
|
||||||
return ERROR_NOT_IMPLEMENTED;
|
return ERROR_NOT_IMPLEMENTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct target *rtos_swbp_target(struct target *target, target_addr_t address,
|
||||||
|
uint32_t length, enum breakpoint_type type)
|
||||||
|
{
|
||||||
|
if (target->rtos->type->swbp_target)
|
||||||
|
return target->rtos->type->swbp_target(target->rtos, address, length, type);
|
||||||
|
return target;
|
||||||
|
}
|
||||||
|
|
|
@ -20,6 +20,7 @@
|
||||||
#define OPENOCD_RTOS_RTOS_H
|
#define OPENOCD_RTOS_RTOS_H
|
||||||
|
|
||||||
#include "server/server.h"
|
#include "server/server.h"
|
||||||
|
#include "target/breakpoints.h"
|
||||||
#include "target/target.h"
|
#include "target/target.h"
|
||||||
#include <helper/jim-nvp.h>
|
#include <helper/jim-nvp.h>
|
||||||
|
|
||||||
|
@ -103,6 +104,12 @@ struct rtos_type {
|
||||||
uint8_t *buffer);
|
uint8_t *buffer);
|
||||||
int (*write_buffer)(struct rtos *rtos, target_addr_t address, uint32_t size,
|
int (*write_buffer)(struct rtos *rtos, target_addr_t address, uint32_t size,
|
||||||
const uint8_t *buffer);
|
const uint8_t *buffer);
|
||||||
|
/* When a software breakpoint is set, it is set on only one target,
|
||||||
|
* because we assume memory is shared across them. By default this is the
|
||||||
|
* first target in the SMP group. Override this function to have
|
||||||
|
* breakpoint_add() use a different target. */
|
||||||
|
struct target * (*swbp_target)(struct rtos *rtos, target_addr_t address,
|
||||||
|
uint32_t length, enum breakpoint_type type);
|
||||||
};
|
};
|
||||||
|
|
||||||
struct stack_register_offset {
|
struct stack_register_offset {
|
||||||
|
@ -166,5 +173,7 @@ int rtos_read_buffer(struct target *target, target_addr_t address,
|
||||||
uint32_t size, uint8_t *buffer);
|
uint32_t size, uint8_t *buffer);
|
||||||
int rtos_write_buffer(struct target *target, target_addr_t address,
|
int rtos_write_buffer(struct target *target, target_addr_t address,
|
||||||
uint32_t size, const uint8_t *buffer);
|
uint32_t size, const uint8_t *buffer);
|
||||||
|
struct target *rtos_swbp_target(struct target *target, target_addr_t address,
|
||||||
|
uint32_t length, enum breakpoint_type type);
|
||||||
|
|
||||||
#endif /* OPENOCD_RTOS_RTOS_H */
|
#endif /* OPENOCD_RTOS_RTOS_H */
|
||||||
|
|
|
@ -26,6 +26,7 @@
|
||||||
#include "target.h"
|
#include "target.h"
|
||||||
#include <helper/log.h>
|
#include <helper/log.h>
|
||||||
#include "breakpoints.h"
|
#include "breakpoints.h"
|
||||||
|
#include "rtos/rtos.h"
|
||||||
|
|
||||||
static const char * const breakpoint_type_strings[] = {
|
static const char * const breakpoint_type_strings[] = {
|
||||||
"hardware",
|
"hardware",
|
||||||
|
@ -218,14 +219,16 @@ int breakpoint_add(struct target *target,
|
||||||
{
|
{
|
||||||
int retval = ERROR_OK;
|
int retval = ERROR_OK;
|
||||||
if (target->smp) {
|
if (target->smp) {
|
||||||
struct target_list *head;
|
struct target_list *head = target->head;
|
||||||
struct target *curr;
|
if (type == BKPT_SOFT) {
|
||||||
head = target->head;
|
struct target *curr = head->target;
|
||||||
if (type == BKPT_SOFT)
|
if (target->rtos)
|
||||||
return breakpoint_add_internal(head->target, address, length, type);
|
curr = rtos_swbp_target(target, address, length, type);
|
||||||
|
return breakpoint_add_internal(curr, address, length, type);
|
||||||
|
}
|
||||||
|
|
||||||
while (head) {
|
while (head) {
|
||||||
curr = head->target;
|
struct target *curr = head->target;
|
||||||
retval = breakpoint_add_internal(curr, address, length, type);
|
retval = breakpoint_add_internal(curr, address, length, type);
|
||||||
if (retval != ERROR_OK)
|
if (retval != ERROR_OK)
|
||||||
return retval;
|
return retval;
|
||||||
|
|
Loading…
Reference in New Issue