TCF Agent: get_reg_definitions may return NULL when context proxy is used
diff --git a/agent/machine/a64/tcf/stack-crawl-a64.c b/agent/machine/a64/tcf/stack-crawl-a64.c
index 46aeea8..506d21b 100644
--- a/agent/machine/a64/tcf/stack-crawl-a64.c
+++ b/agent/machine/a64/tcf/stack-crawl-a64.c
@@ -1156,6 +1156,11 @@
int interrupt_handler = 0;
unsigned i;
+ if (defs == NULL) {
+ set_errno(ERR_OTHER, "Context has no registers");
+ return -1;
+ }
+
stk_ctx = frame->ctx;
stk_frame = frame;
memset(&mem_data, 0, sizeof(mem_data));
diff --git a/agent/machine/arm/tcf/cpudefs-mdep.c b/agent/machine/arm/tcf/cpudefs-mdep.c
index 9330f21..cefe28c 100644
--- a/agent/machine/arm/tcf/cpudefs-mdep.c
+++ b/agent/machine/arm/tcf/cpudefs-mdep.c
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2013-2019 Stanislav Yakovlev and others.
+ * Copyright (c) 2013-2020 Stanislav Yakovlev and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Eclipse Distribution License v1.0 which accompany this distribution.
@@ -258,7 +258,7 @@
cr |= 0x1 << 22;
cr |= 0xf << 5;
}
- cr |= 0x7u;
+ cr |= 0x7;
if (ptrace(PTRACE_SETHBPREGS, pid, 1, &vr) < 0) return -1;
}
else if (cb != NULL) {
diff --git a/agent/machine/arm/tcf/stack-crawl-arm.c b/agent/machine/arm/tcf/stack-crawl-arm.c
index 35f6264..83ecfc4 100644
--- a/agent/machine/arm/tcf/stack-crawl-arm.c
+++ b/agent/machine/arm/tcf/stack-crawl-arm.c
@@ -2475,6 +2475,11 @@
for (i = 0; i < MEM_CACHE_SIZE; i++) mem_cache[i].size = 0;
#endif
+ if (defs == NULL) {
+ set_errno(ERR_OTHER, "Context has no registers");
+ return -1;
+ }
+
stk_ctx = frame->ctx;
stk_frame = frame;
memset(®_data, 0, sizeof(reg_data));
diff --git a/agent/machine/microblaze/tcf/stack-crawl-microblaze.c b/agent/machine/microblaze/tcf/stack-crawl-microblaze.c
index e3fa571..aa15622 100644
--- a/agent/machine/microblaze/tcf/stack-crawl-microblaze.c
+++ b/agent/machine/microblaze/tcf/stack-crawl-microblaze.c
@@ -1103,6 +1103,7 @@
}
int crawl_stack_frame_microblaze(StackFrame * frame, StackFrame * down) {
+ RegisterDefinition * defs = get_reg_definitions(frame->ctx);
RegisterDefinition * def = NULL;
uint64_t pc = 0;
@@ -1111,6 +1112,11 @@
for (i = 0; i < MEM_CACHE_SIZE; i++) mem_cache[i].size = 0;
#endif
+ if (defs == NULL) {
+ set_errno(ERR_OTHER, "Context has no registers");
+ return -1;
+ }
+
reg_size = 4;
stk_ctx = frame->ctx;
memset(®_data, 0, sizeof(reg_data));
@@ -1118,7 +1124,7 @@
branch_pos = 0;
branch_cnt = 0;
- for (def = get_reg_definitions(stk_ctx); def->name; def++) {
+ for (def = defs; def->name; def++) {
if (def->dwarf_id == 0) reg_size = def->size;
if (def->dwarf_id < 0 || def->dwarf_id >= REG_DATA_SIZE) continue;
if (read_reg_value(frame, def, ®_data[def->dwarf_id].v) < 0) continue;
@@ -1129,7 +1135,7 @@
if (trace_instructions() < 0) return -1;
- for (def = get_reg_definitions(stk_ctx); def->name; def++) {
+ for (def = defs; def->name; def++) {
if (def->dwarf_id < 0 || def->dwarf_id >= REG_DATA_SIZE) continue;
if (chk_loaded(def->dwarf_id) < 0) continue;
if (!reg_data[def->dwarf_id].o) continue;
diff --git a/agent/machine/riscv/tcf/stack-crawl-riscv.c b/agent/machine/riscv/tcf/stack-crawl-riscv.c
index 026888a..6b3ec82 100644
--- a/agent/machine/riscv/tcf/stack-crawl-riscv.c
+++ b/agent/machine/riscv/tcf/stack-crawl-riscv.c
@@ -1380,6 +1380,11 @@
RegisterDefinition * def = NULL;
unsigned i;
+ if (defs == NULL) {
+ set_errno(ERR_OTHER, "Context has no registers");
+ return -1;
+ }
+
stk_ctx = frame->ctx;
stk_frame = frame;
memset(&mem_data, 0, sizeof(mem_data));
diff --git a/agent/system/GNU/Linux/tcf/context-linux.c b/agent/system/GNU/Linux/tcf/context-linux.c
index e42511c..51692b1 100644
--- a/agent/system/GNU/Linux/tcf/context-linux.c
+++ b/agent/system/GNU/Linux/tcf/context-linux.c
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2007-2019 Wind River Systems, Inc. and others.
+ * Copyright (c) 2007-2020 Wind River Systems, Inc. and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Eclipse Distribution License v1.0 which accompany this distribution.
@@ -397,12 +397,14 @@
if (error) {
RegisterDefinition * def = get_reg_definitions(ctx);
- while (def->name != NULL && (def->offset > i || def->offset + def->size <= i)) def++;
- if (error != ESRCH || !EXT(ctx->parent)->sigkill_posted) {
- trace(LOG_ALWAYS, "error: writing register %s failed: ctx %#" PRIxPTR ", id %s, error %d %s",
- def->name ? def->name : "?", (uintptr_t)ctx, ctx->id, error, errno_to_str(error));
+ if (def != NULL) {
+ while (def->name != NULL && (def->offset > i || def->offset + def->size <= i)) def++;
+ if (error != ESRCH || !EXT(ctx->parent)->sigkill_posted) {
+ trace(LOG_ALWAYS, "error: writing register %s failed: ctx %#" PRIxPTR ", id %s, error %d %s",
+ def->name ? def->name : "?", (uintptr_t)ctx, ctx->id, error, errno_to_str(error));
+ }
+ if (def->name) error = set_fmt_errno(error, "Cannot write register %s", def->name);
}
- if (def->name) error = set_fmt_errno(error, "Cannot write register %s", def->name);
errno = error;
return -1;
}
diff --git a/agent/tcf/framework/cpudefs.c b/agent/tcf/framework/cpudefs.c
index 0615739..8db5a72 100644
--- a/agent/tcf/framework/cpudefs.c
+++ b/agent/tcf/framework/cpudefs.c
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2007-2019 Wind River Systems, Inc. and others.
+ * Copyright (c) 2007-2020 Wind River Systems, Inc. and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Eclipse Distribution License v1.0 which accompany this distribution.
@@ -242,6 +242,7 @@
int id2register(const char * id, Context ** ctx, int * frame, RegisterDefinition ** reg_def) {
const char * ctx_id = NULL;
+ RegisterDefinition * defs = NULL;
unsigned reg_num = 0;
*ctx = NULL;
@@ -258,7 +259,12 @@
errno = ERR_ALREADY_EXITED;
return -1;
}
- *reg_def = get_reg_definitions(*ctx) + reg_num;
+ defs = get_reg_definitions(*ctx);
+ if (defs == NULL) {
+ set_errno(ERR_OTHER, "Context has no registers");
+ return -1;
+ }
+ *reg_def = defs + reg_num;
return 0;
}
diff --git a/agent/tcf/main/gdb-rsp.c b/agent/tcf/main/gdb-rsp.c
index 49c8b97..92442f1 100644
--- a/agent/tcf/main/gdb-rsp.c
+++ b/agent/tcf/main/gdb-rsp.c
@@ -328,6 +328,7 @@
if (r->id >= 0) {
RegisterDefinition * def = get_reg_definitions(t->ctx);
+ if (def == NULL) return NULL;
while (def->name != NULL) {
if (def->dwarf_id == r->id) return def;
def++;
diff --git a/agent/tcf/services/funccall.c b/agent/tcf/services/funccall.c
index dca820a..a5b3f9a 100644
--- a/agent/tcf/services/funccall.c
+++ b/agent/tcf/services/funccall.c
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2012 Wind River Systems, Inc. and others.
+ * Copyright (c) 2012-2020 Wind River Systems, Inc. and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Eclipse Distribution License v1.0 which accompany this distribution.
@@ -227,18 +227,20 @@
static void save_registers(void) {
unsigned cnt = 0;
- RegisterDefinition * r;
RegisterDefinition * regs = get_reg_definitions(info->ctx);
- for (r = regs; r->name != NULL; r++) {
- if (r->dwarf_id < 0) continue;
- if (r->size == 0) continue;
- cnt++;
- }
- info->saveregs = (RegisterDefinition **)tmp_alloc(sizeof(RegisterDefinition *) * cnt);
- for (r = regs; r->name != NULL; r++) {
- if (r->dwarf_id < 0) continue;
- if (r->size == 0) continue;
- info->saveregs[info->saveregs_cnt++] = r;
+ if (regs != NULL) {
+ RegisterDefinition * r;
+ for (r = regs; r->name != NULL; r++) {
+ if (r->dwarf_id < 0) continue;
+ if (r->size == 0) continue;
+ cnt++;
+ }
+ info->saveregs = (RegisterDefinition **)tmp_alloc(sizeof(RegisterDefinition *) * cnt);
+ for (r = regs; r->name != NULL; r++) {
+ if (r->dwarf_id < 0) continue;
+ if (r->size == 0) continue;
+ info->saveregs[info->saveregs_cnt++] = r;
+ }
}
assert(info->saveregs_cnt == cnt);
}
diff --git a/agent/tcf/services/stacktrace.c b/agent/tcf/services/stacktrace.c
index ef4622c..687898f 100644
--- a/agent/tcf/services/stacktrace.c
+++ b/agent/tcf/services/stacktrace.c
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2007-2017 Wind River Systems, Inc. and others.
+ * Copyright (c) 2007-2020 Wind River Systems, Inc. and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Eclipse Distribution License v1.0 which accompany this distribution.
@@ -153,7 +153,7 @@
StackFrame * prev = stk->frames + stk->frame_cnt - 1;
down->ctx = ctx;
down->fp = frame->fp;
- while (def->name != NULL) {
+ while (def && def->name) {
if (def->dwarf_id >= 0) {
#if ENABLE_StackRegisterLocations
cmd.args.reg = def;
@@ -269,7 +269,7 @@
uint64_t v;
RegisterDefinition * def;
trace(LOG_STACK, "Frame %d", stack->frame_cnt - 1);
- for (def = get_reg_definitions(ctx); def && def->name != NULL; def++) {
+ for (def = get_reg_definitions(ctx); def && def->name; def++) {
if (def->no_read || def->read_once || def->bits || !def->size) continue;
if (read_reg_value(frame, def, &v) != 0) continue;
trace(LOG_STACK, " %-8s %16" PRIx64, def->name, v);
@@ -308,7 +308,7 @@
uint8_t * buf0 = (uint8_t *)tmp_alloc(buf_size);
uint8_t * buf1 = (uint8_t *)tmp_alloc(buf_size);
RegisterDefinition * def;
- for (def = get_reg_definitions(ctx); def->name != NULL; def++) {
+ for (def = get_reg_definitions(ctx); def && def->name; def++) {
int f0, f1;
if (buf_size < def->size) {
buf_size = def->size;