aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/kernel/traps.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/kernel/traps.c')
-rw-r--r--arch/arm/kernel/traps.c44
1 files changed, 29 insertions, 15 deletions
diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c
index 79abc4ddc0cf..57eb0f6f6005 100644
--- a/arch/arm/kernel/traps.c
+++ b/arch/arm/kernel/traps.c
@@ -27,6 +27,7 @@
27#include <asm/system.h> 27#include <asm/system.h>
28#include <asm/unistd.h> 28#include <asm/unistd.h>
29#include <asm/traps.h> 29#include <asm/traps.h>
30#include <asm/unwind.h>
30 31
31#include "ptrace.h" 32#include "ptrace.h"
32#include "signal.h" 33#include "signal.h"
@@ -61,6 +62,7 @@ void dump_backtrace_entry(unsigned long where, unsigned long from, unsigned long
61 dump_mem("Exception stack", frame + 4, frame + 4 + sizeof(struct pt_regs)); 62 dump_mem("Exception stack", frame + 4, frame + 4 + sizeof(struct pt_regs));
62} 63}
63 64
65#ifndef CONFIG_ARM_UNWIND
64/* 66/*
65 * Stack pointers should always be within the kernels view of 67 * Stack pointers should always be within the kernels view of
66 * physical memory. If it is not there, then we can't dump 68 * physical memory. If it is not there, then we can't dump
@@ -74,6 +76,7 @@ static int verify_stack(unsigned long sp)
74 76
75 return 0; 77 return 0;
76} 78}
79#endif
77 80
78/* 81/*
79 * Dump out the contents of some memory nicely... 82 * Dump out the contents of some memory nicely...
@@ -150,13 +153,33 @@ static void dump_instr(struct pt_regs *regs)
150 set_fs(fs); 153 set_fs(fs);
151} 154}
152 155
156#ifdef CONFIG_ARM_UNWIND
157static inline void dump_backtrace(struct pt_regs *regs, struct task_struct *tsk)
158{
159 unwind_backtrace(regs, tsk);
160}
161#else
153static void dump_backtrace(struct pt_regs *regs, struct task_struct *tsk) 162static void dump_backtrace(struct pt_regs *regs, struct task_struct *tsk)
154{ 163{
155 unsigned int fp; 164 unsigned int fp, mode;
156 int ok = 1; 165 int ok = 1;
157 166
158 printk("Backtrace: "); 167 printk("Backtrace: ");
159 fp = regs->ARM_fp; 168
169 if (!tsk)
170 tsk = current;
171
172 if (regs) {
173 fp = regs->ARM_fp;
174 mode = processor_mode(regs);
175 } else if (tsk != current) {
176 fp = thread_saved_fp(tsk);
177 mode = 0x10;
178 } else {
179 asm("mov %0, fp" : "=r" (fp) : : "cc");
180 mode = 0x10;
181 }
182
160 if (!fp) { 183 if (!fp) {
161 printk("no frame pointer"); 184 printk("no frame pointer");
162 ok = 0; 185 ok = 0;
@@ -168,29 +191,20 @@ static void dump_backtrace(struct pt_regs *regs, struct task_struct *tsk)
168 printk("\n"); 191 printk("\n");
169 192
170 if (ok) 193 if (ok)
171 c_backtrace(fp, processor_mode(regs)); 194 c_backtrace(fp, mode);
172} 195}
196#endif
173 197
174void dump_stack(void) 198void dump_stack(void)
175{ 199{
176 __backtrace(); 200 dump_backtrace(NULL, NULL);
177} 201}
178 202
179EXPORT_SYMBOL(dump_stack); 203EXPORT_SYMBOL(dump_stack);
180 204
181void show_stack(struct task_struct *tsk, unsigned long *sp) 205void show_stack(struct task_struct *tsk, unsigned long *sp)
182{ 206{
183 unsigned long fp; 207 dump_backtrace(NULL, tsk);
184
185 if (!tsk)
186 tsk = current;
187
188 if (tsk != current)
189 fp = thread_saved_fp(tsk);
190 else
191 asm("mov %0, fp" : "=r" (fp) : : "cc");
192
193 c_backtrace(fp, 0x10);
194 barrier(); 208 barrier();
195} 209}
196 210