|
@@ -28,6 +28,7 @@
|
|
#include <linux/ptrace.h>
|
|
#include <linux/ptrace.h>
|
|
#include <linux/user.h>
|
|
#include <linux/user.h>
|
|
#include <linux/signal.h>
|
|
#include <linux/signal.h>
|
|
|
|
+#include <linux/syscalls.h>
|
|
|
|
|
|
#include <asm/io.h>
|
|
#include <asm/io.h>
|
|
#include <asm/uaccess.h>
|
|
#include <asm/uaccess.h>
|
|
@@ -121,61 +122,11 @@ put_fpu_long(struct task_struct *task, unsigned long addr, unsigned long data)
|
|
return 0;
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
|
|
-asmlinkage long sys_ptrace(long request, long pid, long addr, long data)
|
|
|
|
|
|
+
|
|
|
|
+long arch_ptrace(struct task_struct *child, long request, long addr, long data)
|
|
{
|
|
{
|
|
- struct task_struct *child;
|
|
|
|
- extern void poke_real_address_q(unsigned long long addr, unsigned long long data);
|
|
|
|
-#define WPC_DBRMODE 0x0d104008
|
|
|
|
- static int first_call = 1;
|
|
|
|
int ret;
|
|
int ret;
|
|
|
|
|
|
- lock_kernel();
|
|
|
|
-
|
|
|
|
- if (first_call) {
|
|
|
|
- /* Set WPC.DBRMODE to 0. This makes all debug events get
|
|
|
|
- * delivered through RESVEC, i.e. into the handlers in entry.S.
|
|
|
|
- * (If the kernel was downloaded using a remote gdb, WPC.DBRMODE
|
|
|
|
- * would normally be left set to 1, which makes debug events get
|
|
|
|
- * delivered through DBRVEC, i.e. into the remote gdb's
|
|
|
|
- * handlers. This prevents ptrace getting them, and confuses
|
|
|
|
- * the remote gdb.) */
|
|
|
|
- printk("DBRMODE set to 0 to permit native debugging\n");
|
|
|
|
- poke_real_address_q(WPC_DBRMODE, 0);
|
|
|
|
- first_call = 0;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- ret = -EPERM;
|
|
|
|
- if (request == PTRACE_TRACEME) {
|
|
|
|
- /* are we already being traced? */
|
|
|
|
- if (current->ptrace & PT_PTRACED)
|
|
|
|
- goto out;
|
|
|
|
- /* set the ptrace bit in the process flags. */
|
|
|
|
- current->ptrace |= PT_PTRACED;
|
|
|
|
- ret = 0;
|
|
|
|
- goto out;
|
|
|
|
- }
|
|
|
|
- ret = -ESRCH;
|
|
|
|
- read_lock(&tasklist_lock);
|
|
|
|
- child = find_task_by_pid(pid);
|
|
|
|
- if (child)
|
|
|
|
- get_task_struct(child);
|
|
|
|
- read_unlock(&tasklist_lock);
|
|
|
|
- if (!child)
|
|
|
|
- goto out;
|
|
|
|
-
|
|
|
|
- ret = -EPERM;
|
|
|
|
- if (pid == 1) /* you may not mess with init */
|
|
|
|
- goto out_tsk;
|
|
|
|
-
|
|
|
|
- if (request == PTRACE_ATTACH) {
|
|
|
|
- ret = ptrace_attach(child);
|
|
|
|
- goto out_tsk;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- ret = ptrace_check_attach(child, request == PTRACE_KILL);
|
|
|
|
- if (ret < 0)
|
|
|
|
- goto out_tsk;
|
|
|
|
-
|
|
|
|
switch (request) {
|
|
switch (request) {
|
|
/* when I and D space are separate, these will need to be fixed. */
|
|
/* when I and D space are separate, these will need to be fixed. */
|
|
case PTRACE_PEEKTEXT: /* read word at location addr. */
|
|
case PTRACE_PEEKTEXT: /* read word at location addr. */
|
|
@@ -313,13 +264,33 @@ asmlinkage long sys_ptrace(long request, long pid, long addr, long data)
|
|
ret = ptrace_request(child, request, addr, data);
|
|
ret = ptrace_request(child, request, addr, data);
|
|
break;
|
|
break;
|
|
}
|
|
}
|
|
-out_tsk:
|
|
|
|
- put_task_struct(child);
|
|
|
|
-out:
|
|
|
|
- unlock_kernel();
|
|
|
|
return ret;
|
|
return ret;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+asmlinkage int sh64_ptrace(long request, long pid, long addr, long data)
|
|
|
|
+{
|
|
|
|
+ extern void poke_real_address_q(unsigned long long addr, unsigned long long data);
|
|
|
|
+#define WPC_DBRMODE 0x0d104008
|
|
|
|
+ static int first_call = 1;
|
|
|
|
+
|
|
|
|
+ lock_kernel();
|
|
|
|
+ if (first_call) {
|
|
|
|
+ /* Set WPC.DBRMODE to 0. This makes all debug events get
|
|
|
|
+ * delivered through RESVEC, i.e. into the handlers in entry.S.
|
|
|
|
+ * (If the kernel was downloaded using a remote gdb, WPC.DBRMODE
|
|
|
|
+ * would normally be left set to 1, which makes debug events get
|
|
|
|
+ * delivered through DBRVEC, i.e. into the remote gdb's
|
|
|
|
+ * handlers. This prevents ptrace getting them, and confuses
|
|
|
|
+ * the remote gdb.) */
|
|
|
|
+ printk("DBRMODE set to 0 to permit native debugging\n");
|
|
|
|
+ poke_real_address_q(WPC_DBRMODE, 0);
|
|
|
|
+ first_call = 0;
|
|
|
|
+ }
|
|
|
|
+ unlock_kernel();
|
|
|
|
+
|
|
|
|
+ return sys_ptrace(request, pid, addr, data);
|
|
|
|
+}
|
|
|
|
+
|
|
asmlinkage void syscall_trace(void)
|
|
asmlinkage void syscall_trace(void)
|
|
{
|
|
{
|
|
struct task_struct *tsk = current;
|
|
struct task_struct *tsk = current;
|