Merge git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6
[linux-2.6] / arch / avr32 / kernel / ptrace.c
1 /*
2  * Copyright (C) 2004-2006 Atmel Corporation
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License version 2 as
6  * published by the Free Software Foundation.
7  */
8 #undef DEBUG
9 #include <linux/kernel.h>
10 #include <linux/sched.h>
11 #include <linux/mm.h>
12 #include <linux/smp_lock.h>
13 #include <linux/ptrace.h>
14 #include <linux/errno.h>
15 #include <linux/user.h>
16 #include <linux/security.h>
17 #include <linux/unistd.h>
18 #include <linux/notifier.h>
19
20 #include <asm/traps.h>
21 #include <asm/uaccess.h>
22 #include <asm/ocd.h>
23 #include <asm/mmu_context.h>
24 #include <asm/kdebug.h>
25
26 static struct pt_regs *get_user_regs(struct task_struct *tsk)
27 {
28         return (struct pt_regs *)((unsigned long) tsk->thread_info +
29                                   THREAD_SIZE - sizeof(struct pt_regs));
30 }
31
32 static void ptrace_single_step(struct task_struct *tsk)
33 {
34         pr_debug("ptrace_single_step: pid=%u, SR=0x%08lx\n",
35                  tsk->pid, tsk->thread.cpu_context.sr);
36         if (!(tsk->thread.cpu_context.sr & SR_D)) {
37                 /*
38                  * Set a breakpoint at the current pc to force the
39                  * process into debug mode.  The syscall/exception
40                  * exit code will set a breakpoint at the return
41                  * address when this flag is set.
42                  */
43                 pr_debug("ptrace_single_step: Setting TIF_BREAKPOINT\n");
44                 set_tsk_thread_flag(tsk, TIF_BREAKPOINT);
45         }
46
47         /* The monitor code will do the actual step for us */
48         set_tsk_thread_flag(tsk, TIF_SINGLE_STEP);
49 }
50
51 /*
52  * Called by kernel/ptrace.c when detaching
53  *
54  * Make sure any single step bits, etc. are not set
55  */
56 void ptrace_disable(struct task_struct *child)
57 {
58         clear_tsk_thread_flag(child, TIF_SINGLE_STEP);
59 }
60
61 /*
62  * Handle hitting a breakpoint
63  */
64 static void ptrace_break(struct task_struct *tsk, struct pt_regs *regs)
65 {
66         siginfo_t info;
67
68         info.si_signo = SIGTRAP;
69         info.si_errno = 0;
70         info.si_code  = TRAP_BRKPT;
71         info.si_addr  = (void __user *)instruction_pointer(regs);
72
73         pr_debug("ptrace_break: Sending SIGTRAP to PID %u (pc = 0x%p)\n",
74                  tsk->pid, info.si_addr);
75         force_sig_info(SIGTRAP, &info, tsk);
76 }
77
78 /*
79  * Read the word at offset "offset" into the task's "struct user". We
80  * actually access the pt_regs struct stored on the kernel stack.
81  */
82 static int ptrace_read_user(struct task_struct *tsk, unsigned long offset,
83                             unsigned long __user *data)
84 {
85         unsigned long *regs;
86         unsigned long value;
87
88         pr_debug("ptrace_read_user(%p, %#lx, %p)\n",
89                  tsk, offset, data);
90
91         if (offset & 3 || offset >= sizeof(struct user)) {
92                 printk("ptrace_read_user: invalid offset 0x%08lx\n", offset);
93                 return -EIO;
94         }
95
96         regs = (unsigned long *)get_user_regs(tsk);
97
98         value = 0;
99         if (offset < sizeof(struct pt_regs))
100                 value = regs[offset / sizeof(regs[0])];
101
102         return put_user(value, data);
103 }
104
105 /*
106  * Write the word "value" to offset "offset" into the task's "struct
107  * user". We actually access the pt_regs struct stored on the kernel
108  * stack.
109  */
110 static int ptrace_write_user(struct task_struct *tsk, unsigned long offset,
111                              unsigned long value)
112 {
113         unsigned long *regs;
114
115         if (offset & 3 || offset >= sizeof(struct user)) {
116                 printk("ptrace_write_user: invalid offset 0x%08lx\n", offset);
117                 return -EIO;
118         }
119
120         if (offset >= sizeof(struct pt_regs))
121                 return 0;
122
123         regs = (unsigned long *)get_user_regs(tsk);
124         regs[offset / sizeof(regs[0])] = value;
125
126         return 0;
127 }
128
129 static int ptrace_getregs(struct task_struct *tsk, void __user *uregs)
130 {
131         struct pt_regs *regs = get_user_regs(tsk);
132
133         return copy_to_user(uregs, regs, sizeof(*regs)) ? -EFAULT : 0;
134 }
135
136 static int ptrace_setregs(struct task_struct *tsk, const void __user *uregs)
137 {
138         struct pt_regs newregs;
139         int ret;
140
141         ret = -EFAULT;
142         if (copy_from_user(&newregs, uregs, sizeof(newregs)) == 0) {
143                 struct pt_regs *regs = get_user_regs(tsk);
144
145                 ret = -EINVAL;
146                 if (valid_user_regs(&newregs)) {
147                         *regs = newregs;
148                         ret = 0;
149                 }
150         }
151
152         return ret;
153 }
154
155 long arch_ptrace(struct task_struct *child, long request, long addr, long data)
156 {
157         unsigned long tmp;
158         int ret;
159
160         pr_debug("arch_ptrace(%ld, %ld, %#lx, %#lx)\n",
161                  request, child->pid, addr, data);
162
163         pr_debug("ptrace: Enabling monitor mode...\n");
164         __mtdr(DBGREG_DC, __mfdr(DBGREG_DC) | DC_MM | DC_DBE);
165
166         switch (request) {
167         /* Read the word at location addr in the child process */
168         case PTRACE_PEEKTEXT:
169         case PTRACE_PEEKDATA:
170                 ret = access_process_vm(child, addr, &tmp, sizeof(tmp), 0);
171                 if (ret == sizeof(tmp))
172                         ret = put_user(tmp, (unsigned long __user *)data);
173                 else
174                         ret = -EIO;
175                 break;
176
177         case PTRACE_PEEKUSR:
178                 ret = ptrace_read_user(child, addr,
179                                        (unsigned long __user *)data);
180                 break;
181
182         /* Write the word in data at location addr */
183         case PTRACE_POKETEXT:
184         case PTRACE_POKEDATA:
185                 ret = access_process_vm(child, addr, &data, sizeof(data), 1);
186                 if (ret == sizeof(data))
187                         ret = 0;
188                 else
189                         ret = -EIO;
190                 break;
191
192         case PTRACE_POKEUSR:
193                 ret = ptrace_write_user(child, addr, data);
194                 break;
195
196         /* continue and stop at next (return from) syscall */
197         case PTRACE_SYSCALL:
198         /* restart after signal */
199         case PTRACE_CONT:
200                 ret = -EIO;
201                 if (!valid_signal(data))
202                         break;
203                 if (request == PTRACE_SYSCALL)
204                         set_tsk_thread_flag(child, TIF_SYSCALL_TRACE);
205                 else
206                         clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE);
207                 child->exit_code = data;
208                 /* XXX: Are we sure no breakpoints are active here? */
209                 wake_up_process(child);
210                 ret = 0;
211                 break;
212
213         /*
214          * Make the child exit. Best I can do is send it a
215          * SIGKILL. Perhaps it should be put in the status that it
216          * wants to exit.
217          */
218         case PTRACE_KILL:
219                 ret = 0;
220                 if (child->exit_state == EXIT_ZOMBIE)
221                         break;
222                 child->exit_code = SIGKILL;
223                 wake_up_process(child);
224                 break;
225
226         /*
227          * execute single instruction.
228          */
229         case PTRACE_SINGLESTEP:
230                 ret = -EIO;
231                 if (!valid_signal(data))
232                         break;
233                 clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE);
234                 ptrace_single_step(child);
235                 child->exit_code = data;
236                 wake_up_process(child);
237                 ret = 0;
238                 break;
239
240         /* Detach a process that was attached */
241         case PTRACE_DETACH:
242                 ret = ptrace_detach(child, data);
243                 break;
244
245         case PTRACE_GETREGS:
246                 ret = ptrace_getregs(child, (void __user *)data);
247                 break;
248
249         case PTRACE_SETREGS:
250                 ret = ptrace_setregs(child, (const void __user *)data);
251                 break;
252
253         default:
254                 ret = ptrace_request(child, request, addr, data);
255                 break;
256         }
257
258         pr_debug("sys_ptrace returning %d (DC = 0x%08lx)\n", ret, __mfdr(DBGREG_DC));
259         return ret;
260 }
261
262 asmlinkage void syscall_trace(void)
263 {
264         pr_debug("syscall_trace called\n");
265         if (!test_thread_flag(TIF_SYSCALL_TRACE))
266                 return;
267         if (!(current->ptrace & PT_PTRACED))
268                 return;
269
270         pr_debug("syscall_trace: notifying parent\n");
271         /* The 0x80 provides a way for the tracing parent to
272          * distinguish between a syscall stop and SIGTRAP delivery */
273         ptrace_notify(SIGTRAP | ((current->ptrace & PT_TRACESYSGOOD)
274                                  ? 0x80 : 0));
275
276         /*
277          * this isn't the same as continuing with a signal, but it
278          * will do for normal use.  strace only continues with a
279          * signal if the stopping signal is not SIGTRAP.  -brl
280          */
281         if (current->exit_code) {
282                 pr_debug("syscall_trace: sending signal %d to PID %u\n",
283                          current->exit_code, current->pid);
284                 send_sig(current->exit_code, current, 1);
285                 current->exit_code = 0;
286         }
287 }
288
289 asmlinkage void do_debug_priv(struct pt_regs *regs)
290 {
291         unsigned long dc, ds;
292         unsigned long die_val;
293
294         ds = __mfdr(DBGREG_DS);
295
296         pr_debug("do_debug_priv: pc = %08lx, ds = %08lx\n", regs->pc, ds);
297
298         if (ds & DS_SSS)
299                 die_val = DIE_SSTEP;
300         else
301                 die_val = DIE_BREAKPOINT;
302
303         if (notify_die(die_val, regs, 0, SIGTRAP) == NOTIFY_STOP)
304                 return;
305
306         if (likely(ds & DS_SSS)) {
307                 extern void itlb_miss(void);
308                 extern void tlb_miss_common(void);
309                 struct thread_info *ti;
310
311                 dc = __mfdr(DBGREG_DC);
312                 dc &= ~DC_SS;
313                 __mtdr(DBGREG_DC, dc);
314
315                 ti = current_thread_info();
316                 ti->flags |= _TIF_BREAKPOINT;
317
318                 /* The TLB miss handlers don't check thread flags */
319                 if ((regs->pc >= (unsigned long)&itlb_miss)
320                     && (regs->pc <= (unsigned long)&tlb_miss_common)) {
321                         __mtdr(DBGREG_BWA2A, sysreg_read(RAR_EX));
322                         __mtdr(DBGREG_BWC2A, 0x40000001 | (get_asid() << 1));
323                 }
324
325                 /*
326                  * If we're running in supervisor mode, the breakpoint
327                  * will take us where we want directly, no need to
328                  * single step.
329                  */
330                 if ((regs->sr & MODE_MASK) != MODE_SUPERVISOR)
331                         ti->flags |= TIF_SINGLE_STEP;
332         } else {
333                 panic("Unable to handle debug trap at pc = %08lx\n",
334                       regs->pc);
335         }
336 }
337
338 /*
339  * Handle breakpoints, single steps and other debuggy things. To keep
340  * things simple initially, we run with interrupts and exceptions
341  * disabled all the time.
342  */
343 asmlinkage void do_debug(struct pt_regs *regs)
344 {
345         unsigned long dc, ds;
346
347         ds = __mfdr(DBGREG_DS);
348         pr_debug("do_debug: pc = %08lx, ds = %08lx\n", regs->pc, ds);
349
350         if (test_thread_flag(TIF_BREAKPOINT)) {
351                 pr_debug("TIF_BREAKPOINT set\n");
352                 /* We're taking care of it */
353                 clear_thread_flag(TIF_BREAKPOINT);
354                 __mtdr(DBGREG_BWC2A, 0);
355         }
356
357         if (test_thread_flag(TIF_SINGLE_STEP)) {
358                 pr_debug("TIF_SINGLE_STEP set, ds = 0x%08lx\n", ds);
359                 if (ds & DS_SSS) {
360                         dc = __mfdr(DBGREG_DC);
361                         dc &= ~DC_SS;
362                         __mtdr(DBGREG_DC, dc);
363
364                         clear_thread_flag(TIF_SINGLE_STEP);
365                         ptrace_break(current, regs);
366                 }
367         } else {
368                 /* regular breakpoint */
369                 ptrace_break(current, regs);
370         }
371 }