gerrit
2017-05-24 21:12:04 UTC
This is an automated email from Gerrit.
Kamal Dasu (***@gmail.com) just uploaded a new patch set to Gerrit, which you can find at http://openocd.zylin.com/4149
-- gerrit
commit 34a2465d801cc4df4e973f25232f9b2abaee04fc
Author: Kamal Dasu <***@gmail.com>
Date: Mon May 22 16:27:59 2017 -0400
aarch64: Added smp_gdb display context support
When trying to debug SMP kernel there was no way to
change the gdb display context to examine the registers
or look at back trace.
Added the smp_gdb command and a way to show the right
gdb display context for a given coreid. This handling
is similar to the cortex_a target.
Change-Id: I3748a55605907f996829e4deb4ef5d6218e3caf5
Signed-off-by: Kamal Dasu <***@gmail.com>
diff --git a/src/target/aarch64.c b/src/target/aarch64.c
index 5e5d3fc..110788e 100644
--- a/src/target/aarch64.c
+++ b/src/target/aarch64.c
@@ -445,6 +445,10 @@ static int update_halt_gdb(struct target *target, enum target_debug_reason debug
if (debug_reason == DBG_REASON_NOTHALTED) {
LOG_INFO("Halting remaining targets in SMP group");
+ if (target->gdb_service && target->gdb_service->core[0] == -1) {
+ target->gdb_service->target = target;
+ target->gdb_service->core[0] = target->coreid;
+ }
aarch64_halt_smp(target, true);
}
@@ -479,6 +483,21 @@ static int update_halt_gdb(struct target *target, enum target_debug_reason debug
return ERROR_OK;
}
+static struct target *get_aarch64(struct target *target, int32_t coreid)
+{
+ struct target_list *head;
+ struct target *curr;
+
+ head = target->head;
+ while (head != (struct target_list *)NULL) {
+ curr = head->target;
+ if ((curr->coreid == coreid) && (curr->state == TARGET_HALTED))
+ return curr;
+ head = head->next;
+ }
+ return target;
+}
+
/*
* Aarch64 Run control
*/
@@ -489,6 +508,19 @@ static int aarch64_poll(struct target *target)
int retval = ERROR_OK;
int halted;
+ /* toggle to another core is done by gdb as follow */
+ /* maint packet J core_id */
+ /* continue */
+ /* the next polling trigger an halt event sent to gdb */
+ if ((target->state == TARGET_HALTED) && (target->smp) &&
+ (target->gdb_service) &&
+ (target->gdb_service->target == NULL)) {
+ target->gdb_service->target =
+ get_aarch64(target, target->gdb_service->core[1]);
+ target_call_event_callbacks(target, TARGET_EVENT_HALTED);
+ return retval;
+ }
+
retval = aarch64_check_state_one(target,
PRSR_HALT, PRSR_HALT, &halted, NULL);
if (retval != ERROR_OK)
@@ -816,6 +848,16 @@ static int aarch64_resume(struct target *target, int current,
if (target->state != TARGET_HALTED)
return ERROR_TARGET_NOT_HALTED;
+ /* dummy resume for smp toggle in order to reduce gdb impact */
+ if ((target->smp) && (target->gdb_service->core[1] != -1)) {
+ /* simulate a start and halt of target */
+ target->gdb_service->target = NULL;
+ target->gdb_service->core[0] = target->gdb_service->core[1];
+ /* fake resume at next poll we play the target core[1], see poll*/
+ target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
+ return 0;
+ }
+
/*
* If this target is part of a SMP group, prepare the others
* targets for resuming. This involves restoring the complete
@@ -823,6 +865,7 @@ static int aarch64_resume(struct target *target, int current,
* resume events from the trigger matrix.
*/
if (target->smp) {
+ target->gdb_service->core[0] = -1;
retval = aarch64_prep_restart_smp(target, handle_breakpoints, NULL);
if (retval != ERROR_OK)
return retval;
@@ -2369,6 +2412,28 @@ COMMAND_HANDLER(aarch64_handle_smp_on_command)
return ERROR_OK;
}
+COMMAND_HANDLER(aarch64_handle_smp_gdb_command)
+{
+ struct target *target = get_current_target(CMD_CTX);
+ int retval = ERROR_OK;
+ struct target_list *head;
+ head = target->head;
+ if (head != (struct target_list *)NULL) {
+ if (CMD_ARGC == 1) {
+ int coreid = 0;
+ COMMAND_PARSE_NUMBER(int, CMD_ARGV[0], coreid);
+ if (ERROR_OK != retval)
+ return retval;
+ target->gdb_service->core[1] = coreid;
+
+ }
+ command_print(CMD_CTX, "gdb coreid %" PRId32 " -> %" PRId32,
+ target->gdb_service->core[0],
+ target->gdb_service->core[1]);
+ }
+ return ERROR_OK;
+}
+
static const struct command_registration aarch64_exec_command_handlers[] = {
{
.name = "cache_info",
@@ -2397,6 +2462,13 @@ static const struct command_registration aarch64_exec_command_handlers[] = {
.help = "Restart smp handling",
.usage = "",
},
+ {
+ .name = "smp_gdb",
+ .handler = aarch64_handle_smp_gdb_command,
+ .mode = COMMAND_EXEC,
+ .help = "display/fix current core played to gdb",
+ .usage = "",
+ },
COMMAND_REGISTRATION_DONE
};
--
Kamal Dasu (***@gmail.com) just uploaded a new patch set to Gerrit, which you can find at http://openocd.zylin.com/4149
-- gerrit
commit 34a2465d801cc4df4e973f25232f9b2abaee04fc
Author: Kamal Dasu <***@gmail.com>
Date: Mon May 22 16:27:59 2017 -0400
aarch64: Added smp_gdb display context support
When trying to debug SMP kernel there was no way to
change the gdb display context to examine the registers
or look at back trace.
Added the smp_gdb command and a way to show the right
gdb display context for a given coreid. This handling
is similar to the cortex_a target.
Change-Id: I3748a55605907f996829e4deb4ef5d6218e3caf5
Signed-off-by: Kamal Dasu <***@gmail.com>
diff --git a/src/target/aarch64.c b/src/target/aarch64.c
index 5e5d3fc..110788e 100644
--- a/src/target/aarch64.c
+++ b/src/target/aarch64.c
@@ -445,6 +445,10 @@ static int update_halt_gdb(struct target *target, enum target_debug_reason debug
if (debug_reason == DBG_REASON_NOTHALTED) {
LOG_INFO("Halting remaining targets in SMP group");
+ if (target->gdb_service && target->gdb_service->core[0] == -1) {
+ target->gdb_service->target = target;
+ target->gdb_service->core[0] = target->coreid;
+ }
aarch64_halt_smp(target, true);
}
@@ -479,6 +483,21 @@ static int update_halt_gdb(struct target *target, enum target_debug_reason debug
return ERROR_OK;
}
+static struct target *get_aarch64(struct target *target, int32_t coreid)
+{
+ struct target_list *head;
+ struct target *curr;
+
+ head = target->head;
+ while (head != (struct target_list *)NULL) {
+ curr = head->target;
+ if ((curr->coreid == coreid) && (curr->state == TARGET_HALTED))
+ return curr;
+ head = head->next;
+ }
+ return target;
+}
+
/*
* Aarch64 Run control
*/
@@ -489,6 +508,19 @@ static int aarch64_poll(struct target *target)
int retval = ERROR_OK;
int halted;
+ /* toggle to another core is done by gdb as follow */
+ /* maint packet J core_id */
+ /* continue */
+ /* the next polling trigger an halt event sent to gdb */
+ if ((target->state == TARGET_HALTED) && (target->smp) &&
+ (target->gdb_service) &&
+ (target->gdb_service->target == NULL)) {
+ target->gdb_service->target =
+ get_aarch64(target, target->gdb_service->core[1]);
+ target_call_event_callbacks(target, TARGET_EVENT_HALTED);
+ return retval;
+ }
+
retval = aarch64_check_state_one(target,
PRSR_HALT, PRSR_HALT, &halted, NULL);
if (retval != ERROR_OK)
@@ -816,6 +848,16 @@ static int aarch64_resume(struct target *target, int current,
if (target->state != TARGET_HALTED)
return ERROR_TARGET_NOT_HALTED;
+ /* dummy resume for smp toggle in order to reduce gdb impact */
+ if ((target->smp) && (target->gdb_service->core[1] != -1)) {
+ /* simulate a start and halt of target */
+ target->gdb_service->target = NULL;
+ target->gdb_service->core[0] = target->gdb_service->core[1];
+ /* fake resume at next poll we play the target core[1], see poll*/
+ target_call_event_callbacks(target, TARGET_EVENT_RESUMED);
+ return 0;
+ }
+
/*
* If this target is part of a SMP group, prepare the others
* targets for resuming. This involves restoring the complete
@@ -823,6 +865,7 @@ static int aarch64_resume(struct target *target, int current,
* resume events from the trigger matrix.
*/
if (target->smp) {
+ target->gdb_service->core[0] = -1;
retval = aarch64_prep_restart_smp(target, handle_breakpoints, NULL);
if (retval != ERROR_OK)
return retval;
@@ -2369,6 +2412,28 @@ COMMAND_HANDLER(aarch64_handle_smp_on_command)
return ERROR_OK;
}
+COMMAND_HANDLER(aarch64_handle_smp_gdb_command)
+{
+ struct target *target = get_current_target(CMD_CTX);
+ int retval = ERROR_OK;
+ struct target_list *head;
+ head = target->head;
+ if (head != (struct target_list *)NULL) {
+ if (CMD_ARGC == 1) {
+ int coreid = 0;
+ COMMAND_PARSE_NUMBER(int, CMD_ARGV[0], coreid);
+ if (ERROR_OK != retval)
+ return retval;
+ target->gdb_service->core[1] = coreid;
+
+ }
+ command_print(CMD_CTX, "gdb coreid %" PRId32 " -> %" PRId32,
+ target->gdb_service->core[0],
+ target->gdb_service->core[1]);
+ }
+ return ERROR_OK;
+}
+
static const struct command_registration aarch64_exec_command_handlers[] = {
{
.name = "cache_info",
@@ -2397,6 +2462,13 @@ static const struct command_registration aarch64_exec_command_handlers[] = {
.help = "Restart smp handling",
.usage = "",
},
+ {
+ .name = "smp_gdb",
+ .handler = aarch64_handle_smp_gdb_command,
+ .mode = COMMAND_EXEC,
+ .help = "display/fix current core played to gdb",
+ .usage = "",
+ },
COMMAND_REGISTRATION_DONE
};
--