Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/sh3/sh3 db_stack_trace_print: support trace/[at], s...



details:   https://anonhg.NetBSD.org/src/rev/22a21ac0452b
branches:  trunk
changeset: 789106:22a21ac0452b
user:      uwe <uwe%NetBSD.org@localhost>
date:      Tue Aug 06 21:41:01 2013 +0000

description:
db_stack_trace_print: support trace/[at], starting trace from switchframe.

diffstat:

 sys/arch/sh3/sh3/db_trace.c |  75 ++++++++++++++++++++++++++++++++++++++++----
 1 files changed, 67 insertions(+), 8 deletions(-)

diffs (101 lines):

diff -r 86b5c1625c4a -r 22a21ac0452b sys/arch/sh3/sh3/db_trace.c
--- a/sys/arch/sh3/sh3/db_trace.c       Tue Aug 06 20:49:15 2013 +0000
+++ b/sys/arch/sh3/sh3/db_trace.c       Tue Aug 06 21:41:01 2013 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: db_trace.c,v 1.23 2008/06/08 22:02:08 uwe Exp $        */
+/*     $NetBSD: db_trace.c,v 1.24 2013/08/06 21:41:01 uwe Exp $        */
 
 /*-
  * Copyright (c) 2000 Tsubai Masanari.  All rights reserved.
@@ -27,7 +27,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: db_trace.c,v 1.23 2008/06/08 22:02:08 uwe Exp $");
+__KERNEL_RCSID(0, "$NetBSD: db_trace.c,v 1.24 2013/08/06 21:41:01 uwe Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -82,17 +82,76 @@
        struct trapframe *tf;
        db_addr_t callpc, frame, lastframe;
        uint32_t vbr;
+       bool kernel_only = true;
+       bool lwpid = false;
+       bool lwpaddr = false;
+       const char *cp;
+       char c;
 
        __asm volatile("stc vbr, %0" : "=r"(vbr));
 
-       tf = &ddb_regs;
+       cp = modif;
+       while ((c = *cp++) != 0) {
+               if (c == 'a')
+                       lwpaddr = true;
+               else if (c == 't')
+                       lwpid = true;
+               else if (c == 'u')
+                       kernel_only = false;
+       }
+
+       if (lwpaddr && lwpid) {
+               db_printf("only one of /a or /t can be specified\n");
+               return;
+       }
+       if ((lwpaddr || lwpid) && !have_addr) {
+               db_printf("%s required\n", lwpaddr ? "address" : "pid");
+               return;
+       }
+
 
-       frame = tf->tf_r14;
-       callpc = tf->tf_spc;
+       if (!have_addr) {
+               tf = &ddb_regs;
+               frame = tf->tf_r14;
+               callpc = tf->tf_spc;
+               if (callpc == 0) {
+                       (*print)("calling through null pointer?\n");
+                       callpc = tf->tf_pr;
+               }
+       }
+       else if (lwpaddr || lwpid) {
+               struct proc *p;
+               struct lwp *l;
+               struct pcb *pcb;
 
-       if (callpc == 0) {
-               (*print)("calling through null pointer?\n");
-               callpc = tf->tf_pr;
+               if (lwpaddr) {
+                       l = (struct lwp *)addr;
+                       p = l->l_proc;
+                       (*print)("trace: lwp addr %p pid %d ",
+                                (void *)addr, p->p_pid);
+               }
+               else {
+                       pid_t pid = (pid_t)addr;
+                       (*print)("trace: pid %d ", pid);
+                       p = proc_find_raw(pid);
+                       if (p == NULL) {
+                               (*print)("not found\n");
+                               return;
+                       }
+                       l = LIST_FIRST(&p->p_lwps);
+               }
+               KASSERT(l != NULL);
+               (*print)("lid %d ", l->l_lid);
+               pcb = lwp_getpcb(l);
+               tf = (struct trapframe *)pcb->pcb_sf.sf_r6_bank;
+               frame = pcb->pcb_sf.sf_r14;
+               callpc = pcb->pcb_sf.sf_pr;
+               (*print)("at %p\n", frame);
+       }
+       else {
+               /* XXX */
+               db_printf("trace by frame address is not supported\n");
+               return;
        }
 
        lastframe = 0;



Home | Main Index | Thread Index | Old Index