target: Add target controller structure for indirect calls back to host.

This commit is contained in:
Gareth McMullin 2016-07-01 13:10:44 +12:00
parent 5832d8a42a
commit b03cc59bea
4 changed files with 37 additions and 30 deletions

View File

@ -47,8 +47,9 @@ static void handle_q_packet(char *packet, int len);
static void handle_v_packet(char *packet, int len); static void handle_v_packet(char *packet, int len);
static void handle_z_packet(char *packet, int len); static void handle_z_packet(char *packet, int len);
static void gdb_target_destroy_callback(target *t) static void gdb_target_destroy_callback(struct target_controller *tc, target *t)
{ {
(void)tc;
if (cur_target == t) if (cur_target == t)
cur_target = NULL; cur_target = NULL;
@ -56,6 +57,18 @@ static void gdb_target_destroy_callback(target *t)
last_target = NULL; last_target = NULL;
} }
static void gdb_target_printf(struct target_controller *tc,
const char *fmt, va_list ap)
{
(void)tc;
gdb_voutf(fmt, ap);
}
static struct target_controller gdb_controller = {
.destroy_callback = gdb_target_destroy_callback,
.printf = gdb_target_printf,
};
void void
gdb_main(void) gdb_main(void)
{ {
@ -227,7 +240,7 @@ gdb_main(void)
target_reset(cur_target); target_reset(cur_target);
else if(last_target) { else if(last_target) {
cur_target = target_attach(last_target, cur_target = target_attach(last_target,
gdb_target_destroy_callback); &gdb_controller);
target_reset(cur_target); target_reset(cur_target);
} }
break; break;
@ -323,7 +336,7 @@ handle_q_packet(char *packet, int len)
if((!cur_target) && last_target) { if((!cur_target) && last_target) {
/* Attach to last target if detached. */ /* Attach to last target if detached. */
cur_target = target_attach(last_target, cur_target = target_attach(last_target,
gdb_target_destroy_callback); &gdb_controller);
} }
if (!cur_target) { if (!cur_target) {
gdb_putpacketz("E01"); gdb_putpacketz("E01");
@ -336,7 +349,7 @@ handle_q_packet(char *packet, int len)
if((!cur_target) && last_target) { if((!cur_target) && last_target) {
/* Attach to last target if detached. */ /* Attach to last target if detached. */
cur_target = target_attach(last_target, cur_target = target_attach(last_target,
gdb_target_destroy_callback); &gdb_controller);
} }
if (!cur_target) { if (!cur_target) {
gdb_putpacketz("E01"); gdb_putpacketz("E01");
@ -365,7 +378,7 @@ handle_v_packet(char *packet, int plen)
if (sscanf(packet, "vAttach;%08lx", &addr) == 1) { if (sscanf(packet, "vAttach;%08lx", &addr) == 1) {
/* Attach to remote target processor */ /* Attach to remote target processor */
cur_target = target_attach_n(addr, gdb_target_destroy_callback); cur_target = target_attach_n(addr, &gdb_controller);
if(cur_target) if(cur_target)
gdb_putpacketz("T05"); gdb_putpacketz("T05");
else else
@ -378,7 +391,7 @@ handle_v_packet(char *packet, int plen)
gdb_putpacketz("T05"); gdb_putpacketz("T05");
} else if(last_target) { } else if(last_target) {
cur_target = target_attach(last_target, cur_target = target_attach(last_target,
gdb_target_destroy_callback); &gdb_controller);
/* If we were able to attach to the target again */ /* If we were able to attach to the target again */
if (cur_target) { if (cur_target) {

View File

@ -33,20 +33,14 @@ int jtag_scan(const uint8_t *lrlens);
bool target_foreach(void (*cb)(int i, target *t, void *context), void *context); bool target_foreach(void (*cb)(int i, target *t, void *context), void *context);
void target_list_free(void); void target_list_free(void);
/* The destroy callback function will be called by target_list_free() just struct target_controller {
* before the target is free'd. This may be because we're scanning for new void (*destroy_callback)(struct target_controller *, target *t);
* targets, or because of a communication failure. The target data may void (*printf)(struct target_controller *, const char *fmt, va_list);
* be assumed to be intact, but the communication medium may not be available, };
* so access methods shouldn't be called.
*
* The callback is installed by target_attach() and only removed by attaching
* with a different callback. It remains intact after target_detach().
*/
typedef void (*target_destroy_callback)(target *t);
/* Halt/resume functions */ /* Halt/resume functions */
target *target_attach(target *t, target_destroy_callback destroy_cb); target *target_attach(target *t, struct target_controller *);
target *target_attach_n(int n, target_destroy_callback destroy_cb); target *target_attach_n(int n, struct target_controller *);
void target_detach(target *t); void target_detach(target *t);
bool target_check_error(target *t); bool target_check_error(target *t);
bool target_attached(target *t); bool target_attached(target *t);

View File

@ -22,6 +22,8 @@
#include "target.h" #include "target.h"
#include "target_internal.h" #include "target_internal.h"
#include <stdarg.h>
target *target_list = NULL; target *target_list = NULL;
target *target_new(void) target *target_new(void)
@ -48,8 +50,8 @@ void target_list_free(void)
while(target_list) { while(target_list) {
target *t = target_list->next; target *t = target_list->next;
if (target_list->destroy_callback) if (target_list->tc)
target_list->destroy_callback(target_list); target_list->tc->destroy_callback(target_list->tc, target_list);
if (target_list->priv) if (target_list->priv)
target_list->priv_free(target_list->priv); target_list->priv_free(target_list->priv);
while (target_list->commands) { while (target_list->commands) {
@ -90,22 +92,22 @@ void target_add_commands(target *t, const struct command_s *cmds, const char *na
tc->next = NULL; tc->next = NULL;
} }
target *target_attach_n(int n, target_destroy_callback destroy_cb) target *target_attach_n(int n, struct target_controller *tc)
{ {
target *t; target *t;
int i; int i;
for(t = target_list, i = 1; t; t = t->next, i++) for(t = target_list, i = 1; t; t = t->next, i++)
if(i == n) if(i == n)
return target_attach(t, destroy_cb); return target_attach(t, tc);
return NULL; return NULL;
} }
target *target_attach(target *t, target_destroy_callback destroy_cb) target *target_attach(target *t, struct target_controller *tc)
{ {
if (t->destroy_callback) if (t->tc)
t->destroy_callback(t); t->tc->destroy_callback(t->tc, t);
t->destroy_callback = destroy_cb; t->tc = tc;
if (!t->attach(t)) if (!t->attach(t))
return NULL; return NULL;
@ -418,13 +420,12 @@ int target_command(target *t, int argc, const char *argv[])
return -1; return -1;
} }
#include "gdb_packet.h"
void tc_printf(target *t, const char *fmt, ...) void tc_printf(target *t, const char *fmt, ...)
{ {
(void)t; (void)t;
va_list ap; va_list ap;
va_start(ap, fmt); va_start(ap, fmt);
gdb_voutf(fmt, ap); t->tc->printf(t->tc, fmt, ap);
va_end(ap); va_end(ap);
} }

View File

@ -70,8 +70,7 @@ struct target_command_s {
struct target_s { struct target_s {
bool attached; bool attached;
/* Notify controlling debugger if target is lost */ struct target_controller *tc;
target_destroy_callback destroy_callback;
/* Attach/Detach funcitons */ /* Attach/Detach funcitons */
bool (*attach)(target *t); bool (*attach)(target *t);