For example, crash_kexec() calls several sub functions.
So even if we find some address which belongs to one of those functions
as a saved lr in a task's stack, it may not be the *last* stackframe.
For our purpose of backtracing, it is not necessary to find the last
frame, but the saved frame pointer should be sane for later use.

This patch adds some check.

Signed-off-by: AKASHI Takahiro <[email protected]>
---
 arm64.c | 32 +++++++++++++++++++++-----------
 1 file changed, 21 insertions(+), 11 deletions(-)

diff --git a/arm64.c b/arm64.c
index 0ac5894..b74d2c4 100644
--- a/arm64.c
+++ b/arm64.c
@@ -1931,9 +1931,9 @@ arm64_back_trace_cmd(struct bt_info *bt)
                        arm64_set_irq_stack(bt);
                        bt->flags |= BT_IRQSTACK;
                }
-               stackframe.fp = GET_STACK_ULONG(bt->bptr - 8);
-               stackframe.pc = GET_STACK_ULONG(bt->bptr);
-               stackframe.sp = bt->bptr + 8;
+               stackframe.fp = GET_STACK_ULONG(bt->bptr);
+               stackframe.pc = GET_STACK_ULONG(bt->bptr + 8);
+               stackframe.sp = bt->bptr + 16;
                bt->frameptr = stackframe.fp;
        } else {
                stackframe.sp = bt->stkptr;
@@ -2098,14 +2098,20 @@ arm64_in_kdump_text(struct bt_info *bt, struct 
arm64_stackframe *frame)
 
        ms = machdep->machspec;
        for (ptr = start - 8; ptr >= base; ptr--) {
-               if ((*ptr >= ms->crash_kexec_start) && (*ptr < 
ms->crash_kexec_end)) {
-                       bt->bptr = ((ulong)ptr - (ulong)base) + 
bt->tc->thread_info;
+               if ((*ptr >= ms->crash_kexec_start) &&
+                   (*ptr < ms->crash_kexec_end) &&
+                   INSTACK(*(ptr - 1), bt)) {
+                       bt->bptr = ((ulong)(ptr - 1) - (ulong)base)
+                                  + bt->tc->thread_info;
                        if (CRASHDEBUG(1))
                                fprintf(fp, "%lx: %lx (crash_kexec)\n", 
bt->bptr, *ptr);
                        return TRUE;
                }
-               if ((*ptr >= ms->crash_save_cpu_start) && (*ptr < 
ms->crash_save_cpu_end)) {
-                       bt->bptr = ((ulong)ptr - (ulong)base) + 
bt->tc->thread_info;
+               if ((*ptr >= ms->crash_save_cpu_start) &&
+                   (*ptr < ms->crash_save_cpu_end) &&
+                   INSTACK(*(ptr - 1), bt)) {
+                       bt->bptr = ((ulong)(ptr - 1) - (ulong)base)
+                                  + bt->tc->thread_info;
                        if (CRASHDEBUG(1))
                                fprintf(fp, "%lx: %lx (crash_save_cpu)\n", 
bt->bptr, *ptr);
                        return TRUE;
@@ -2143,16 +2149,20 @@ arm64_in_kdump_text_on_irq_stack(struct bt_info *bt)
        start = (ulong *)(stackbuf + ms->irq_stack_size);
 
        for (ptr = start - 8; ptr >= base; ptr--) {
-               if ((*ptr >= ms->crash_kexec_start) && (*ptr < 
ms->crash_kexec_end)) {
-                       bt->bptr = ((ulong)ptr - (ulong)base) + stackbase;
+               if ((*ptr >= ms->crash_kexec_start) &&
+                   (*ptr < ms->crash_kexec_end) &&
+                   INSTACK(*(ptr - 1), bt)) {
+                       bt->bptr = ((ulong)(ptr - 1) - (ulong)base) + stackbase;
                        if (CRASHDEBUG(1))
                                fprintf(fp, "%lx: %lx (crash_kexec on IRQ 
stack)\n", 
                                        bt->bptr, *ptr);
                        FREEBUF(stackbuf);
                        return TRUE;
                }
-               if ((*ptr >= ms->crash_save_cpu_start) && (*ptr < 
ms->crash_save_cpu_end)) {
-                       bt->bptr = ((ulong)ptr - (ulong)base) + stackbase;
+               if ((*ptr >= ms->crash_save_cpu_start) &&
+                   (*ptr < ms->crash_save_cpu_end) &&
+                   INSTACK(*(ptr - 1), bt)) {
+                       bt->bptr = ((ulong)(ptr - 1) - (ulong)base) + stackbase;
                        if (CRASHDEBUG(1))
                                fprintf(fp, "%lx: %lx (crash_save_cpu on IRQ 
stack)\n", 
                                        bt->bptr, *ptr);
-- 
2.9.0

--
Crash-utility mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/crash-utility

Reply via email to