Skip to contentSkip to conversation

consolidate sys_ptrace

PATCH New Christoph Hellwig 1 participant 1 message Aug 26, 2005

Subsystems (8)
lore
Share & tools
lore
#0 lore raw

PATCH 1/2 consolidate sys_ptrace

The sys_ptrace boilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it to kernel/ptrace.c and leaves the arch-specific code as arch_ptrace.

Some architectures have a too different ptrace so we have to exclude them. They continue to keep their implementations. For sh64 I had to add a sh64_ptrace wrapper because it does some initialization on the first call. For um I removed an ifdefed SUBARCH_PTRACE_SPECIAL block, but SUBARCH_PTRACE_SPECIAL isn't defined anywhere in the tree.

sys_ptrace is declared in syscalls.h now for architectures that are consolidated, and all these architectures return long from ptrace now (that was not true for some 32bit architectures before). Non-consolidated architectures sometimes still return int and have the prototype in <asm/unistd.h> if at at all. This will be fixes in later patches.

arch/arm/kernel/ptrace.c +1 -48
Index: linux-2.6/arch/arm/kernel/ptrace.c
===================================================================
@@ -648,7 +648,7 @@
 
 #endif
 
-static int do_ptrace(int request, struct task_struct *child, long addr, long data)
+long arch_ptrace(struct task_struct *child, long request, long addr, long data)
 {
 	unsigned long tmp;
 	int ret;
@@ -782,53 +782,6 @@
 	return ret;
 }
 
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data)
-{
-	struct task_struct *child;
-	int ret;
-
-	lock_kernel();
-	ret = -EPERM;
-	if (request == PTRACE_TRACEME) {
-		/* are we already being traced? */
-		if (current->ptrace & PT_PTRACED)
-			goto out;
-		ret = security_ptrace(current->parent, current);
-		if (ret)
-			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)
-		ret = do_ptrace(request, child, addr, data);
-
-out_tsk:
-	put_task_struct(child);
-out:
-	unlock_kernel();
-	return ret;
-}
-
 asmlinkage void syscall_trace(int why, struct pt_regs *regs)
 {
 	unsigned long ip;
arch/arm26/kernel/ptrace.c +1 -48

61 lines not on this page · raw message

arch/frv/kernel/ptrace.c +1 -42

59 lines not on this page · raw message

arch/h8300/kernel/ptrace.c +1 -38
Index: linux-2.6/arch/h8300/kernel/ptrace.c
===================================================================
@@ -57,43 +57,10 @@
 	h8300_disable_trace(child);
 }
 
-asmlinkage int 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;
 	int ret;
 
-	lock_kernel();
-	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) {
 		case PTRACE_PEEKTEXT: /* read word at location addr. */ 
 		case PTRACE_PEEKDATA: {
@@ -251,10 +218,6 @@
 			ret = -EIO;
 			break;
 	}
-out_tsk:
-	put_task_struct(child);
-out:
-	unlock_kernel();
 	return ret;
 }
 
arch/i386/kernel/ptrace.c +2 -42

61 lines not on this page · raw message

arch/m68knommu/kernel/ptrace.c +1 -38
Index: linux-2.6/arch/m68knommu/kernel/ptrace.c
===================================================================
@@ -101,43 +101,10 @@
 	put_reg(child, PT_SR, tmp);
 }
 
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data)
+long arch_ptrace(truct task_struct *child, long request, long addr, long data)
 {
-	struct task_struct *child;
 	int ret;
 
-	lock_kernel();
-	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) {
 		/* when I and D space are separate, these will need to be fixed. */
 		case PTRACE_PEEKTEXT: /* read word at location addr. */ 
@@ -357,10 +324,6 @@
 			ret = -EIO;
 			break;
 	}
-out_tsk:
-	put_task_struct(child);
-out:
-	unlock_kernel();
 	return ret;
 }
 
arch/mips/kernel/ptrace.c +1 -46

62 lines not on this page · raw message

arch/ppc/kernel/ptrace.c +2 -41

58 lines not on this page · raw message

arch/ppc64/kernel/ptrace.c +2 -41

58 lines not on this page · raw message

arch/sh/kernel/ptrace.c +2 -42

60 lines not on this page · raw message

arch/v850/kernel/ptrace.c +1 -40

56 lines not on this page · raw message

arch/x86_64/kernel/ptrace.c +1 -42

59 lines not on this page · raw message

arch/xtensa/kernel/ptrace.c +2 -53

70 lines not on this page · raw message

kernel/ptrace.c +82 -0

85 lines not on this page · raw message

arch/cris/arch-v10/kernel/ptrace.c +2 -49

67 lines not on this page · raw message

arch/cris/arch-v32/kernel/ptrace.c +2 -49

67 lines not on this page · raw message

arch/um/kernel/ptrace.c +2 -48

65 lines not on this page · raw message

include/asm-alpha/ptrace.h +3 -0
Index: linux-2.6/include/asm-alpha/ptrace.h
===================================================================
@@ -67,6 +67,9 @@
 };
 
 #ifdef __KERNEL__
+
+#define __ARCH_SYS_PTRACE	1
+
 #define user_mode(regs) (((regs)->ps & 8) != 0)
 #define instruction_pointer(regs) ((regs)->pc)
 #define profile_pc(regs) instruction_pointer(regs)
include/asm-arm/unistd.h +0 -1
Index: linux-2.6/include/asm-arm/unistd.h
===================================================================
@@ -542,7 +542,6 @@
 asmlinkage int sys_fork(struct pt_regs *regs);
 asmlinkage int sys_vfork(struct pt_regs *regs);
 asmlinkage int sys_pipe(unsigned long *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-arm26/unistd.h +0 -1
Index: linux-2.6/include/asm-arm26/unistd.h
===================================================================
@@ -480,7 +480,6 @@
 asmlinkage int sys_fork(struct pt_regs *regs);
 asmlinkage int sys_vfork(struct pt_regs *regs);
 asmlinkage int sys_pipe(unsigned long *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-cris/unistd.h +0 -1
Index: linux-2.6/include/asm-cris/unistd.h
===================================================================
@@ -367,7 +367,6 @@
 asmlinkage int sys_vfork(long r10, long r11, long r12, long r13,
 			long mof, long srp, struct pt_regs *regs);
 asmlinkage int sys_pipe(unsigned long __user *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-h8300/unistd.h +0 -1
Index: linux-2.6/include/asm-h8300/unistd.h
===================================================================
@@ -528,7 +528,6 @@
 asmlinkage int sys_execve(char *name, char **argv, char **envp,
 			int dummy, ...);
 asmlinkage int sys_pipe(unsigned long *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-i386/unistd.h +0 -1
Index: linux-2.6/include/asm-i386/unistd.h
===================================================================
@@ -448,7 +448,6 @@
 asmlinkage int sys_fork(struct pt_regs regs);
 asmlinkage int sys_vfork(struct pt_regs regs);
 asmlinkage int sys_pipe(unsigned long __user *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 asmlinkage long sys_iopl(unsigned long unused);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
include/asm-ia64/ptrace.h +3 -0
Index: linux-2.6/include/asm-ia64/ptrace.h
===================================================================
@@ -227,6 +227,9 @@
 };
 
 #ifdef __KERNEL__
+
+#define __ARCH_SYS_PTRACE	1
+
 /*
  * We use the ia64_psr(regs)->ri to determine which of the three
  * instructions in bundle (16 bytes) took the sample. Generate
include/asm-m32r/ptrace.h +3 -0
Index: linux-2.6/include/asm-m32r/ptrace.h
===================================================================
@@ -145,6 +145,9 @@
 #define PTRACE_O_TRACESYSGOOD	0x00000001
 
 #ifdef __KERNEL__
+
+#define __ARCH_SYS_PTRACE	1
+
 #if defined(CONFIG_ISA_M32R2) || defined(CONFIG_CHIP_VDEC2)
 #define user_mode(regs) ((M32R_PSW_BPM & (regs)->psw) != 0)
 #elif defined(CONFIG_ISA_M32R)
include/asm-m68knommu/unistd.h +0 -1
Index: linux-2.6/include/asm-m68knommu/unistd.h
===================================================================
@@ -504,7 +504,6 @@
 			unsigned long fd, unsigned long pgoff);
 asmlinkage int sys_execve(char *name, char **argv, char **envp);
 asmlinkage int sys_pipe(unsigned long *fildes);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct pt_regs;
 int sys_request_irq(unsigned int,
 			irqreturn_t (*)(int, void *, struct pt_regs *),
include/asm-mips/unistd.h +0 -1
Index: linux-2.6/include/asm-mips/unistd.h
===================================================================
@@ -1164,7 +1164,6 @@
 			unsigned long fd, unsigned long pgoff);
 asmlinkage int sys_execve(nabi_no_regargs struct pt_regs regs);
 asmlinkage int sys_pipe(nabi_no_regargs struct pt_regs regs);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-parisc/ptrace.h +3 -0
Index: linux-2.6/include/asm-parisc/ptrace.h
===================================================================
@@ -45,6 +45,9 @@
 #define PTRACE_SINGLEBLOCK	12	/* resume execution until next branch */
 #ifdef __KERNEL__
 
+#define __ARCH_SYS_PTRACE	1
+
+
 /* XXX should we use iaoq[1] or iaoq[0] ? */
 #define user_mode(regs)			(((regs)->iaoq[0] & 3) ? 1 : 0)
 #define user_space(regs)		(((regs)->iasq[1] != 0) ? 1 : 0)
include/asm-ppc/unistd.h +0 -1
Index: linux-2.6/include/asm-ppc/unistd.h
===================================================================
@@ -469,7 +469,6 @@
 int sys_vfork(int p1, int p2, int p3, int p4, int p5, int p6,
 		struct pt_regs *regs);
 int sys_pipe(int __user *fildes);
-int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 long sys_rt_sigaction(int sig,
 		      const struct sigaction __user *act,
include/asm-ppc64/unistd.h +0 -1
Index: linux-2.6/include/asm-ppc64/unistd.h
===================================================================
@@ -467,7 +467,6 @@
 		unsigned long p4, unsigned long p5, unsigned long p6,
 		struct pt_regs *regs);
 int sys_pipe(int __user *fildes);
-int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 long sys_rt_sigaction(int sig, const struct sigaction __user *act,
 		      struct sigaction __user *oact, size_t sigsetsize);
include/asm-sh/unistd.h +0 -1
Index: linux-2.6/include/asm-sh/unistd.h
===================================================================
@@ -503,7 +503,6 @@
 asmlinkage int sys_pipe(unsigned long r4, unsigned long r5,
 			unsigned long r6, unsigned long r7,
 			struct pt_regs regs);
-asmlinkage int sys_ptrace(long request, long pid, long addr, long data);
 asmlinkage ssize_t sys_pread_wrapper(unsigned int fd, char *buf,
 				size_t count, long dummy, loff_t pos);
 asmlinkage ssize_t sys_pwrite_wrapper(unsigned int fd, const char *buf,
include/asm-sparc/ptrace.h +3 -0
Index: linux-2.6/include/asm-sparc/ptrace.h
===================================================================
@@ -60,6 +60,9 @@
 #define STACKFRAME_SZ sizeof(struct sparc_stackf)
 
 #ifdef __KERNEL__
+
+#define __ARCH_SYS_PTRACE	1
+
 #define user_mode(regs) (!((regs)->psr & PSR_PS))
 #define instruction_pointer(regs) ((regs)->pc)
 unsigned long profile_pc(struct pt_regs *);
include/asm-sparc64/ptrace.h +3 -0
Index: linux-2.6/include/asm-sparc64/ptrace.h
===================================================================
@@ -94,6 +94,9 @@
 #define STACKFRAME32_SZ	sizeof(struct sparc_stackf32)
 
 #ifdef __KERNEL__
+
+#define __ARCH_SYS_PTRACE	1
+
 #define force_successful_syscall_return()	    \
 do {	current_thread_info()->syscall_noerror = 1; \
 } while (0)
include/asm-v850/unistd.h +0 -1
Index: linux-2.6/include/asm-v850/unistd.h
===================================================================
@@ -452,7 +452,6 @@
 struct pt_regs;
 int sys_execve (char *name, char **argv, char **envp, struct pt_regs *regs);
 int sys_pipe (int *fildes);
-int sys_ptrace(long request, long pid, long addr, long data);
 struct sigaction;
 asmlinkage long sys_rt_sigaction(int sig,
 				const struct sigaction __user *act,
include/asm-x86_64/unistd.h +0 -2
Index: linux-2.6/include/asm-x86_64/unistd.h
===================================================================
@@ -780,8 +780,6 @@
 #include <linux/types.h>
 #include <asm/ptrace.h>
 
-asmlinkage long sys_ptrace(long request, long pid,
-				unsigned long addr, long data);
 asmlinkage long sys_iopl(unsigned int level, struct pt_regs *regs);
 asmlinkage long sys_ioperm(unsigned long from, unsigned long num, int turn_on);
 struct sigaction;
include/linux/ptrace.h +2 -0
Index: linux-2.6/include/linux/ptrace.h
===================================================================
@@ -76,6 +76,8 @@
 #include <linux/compiler.h>		/* For unlikely.  */
 #include <linux/sched.h>		/* For struct task_struct.  */
 
+
+extern long arch_ptrace(struct task_struct *child, long request, long addr, long data);
 extern int ptrace_readdata(struct task_struct *tsk, unsigned long src, char __user *dst, int len);
 extern int ptrace_writedata(struct task_struct *tsk, char __user *src, unsigned long dst, int len);
 extern int ptrace_attach(struct task_struct *tsk);
arch/sh64/kernel/ptrace.c +27 -56

107 lines not on this page · raw message

arch/sh64/kernel/syscalls.S +1 -1
Index: linux-2.6/arch/sh64/kernel/syscalls.S
===================================================================
@@ -46,7 +46,7 @@
 	.long sys_setuid16
 	.long sys_getuid16
 	.long sys_stime			/* 25 */
-	.long sys_ptrace
+	.long sh64_ptrace
 	.long sys_alarm
 	.long sys_fstat
 	.long sys_pause
include/asm-m68k/ptrace.h +1 -0
Index: linux-2.6/include/asm-m68k/ptrace.h
===================================================================
@@ -65,6 +65,7 @@
 #define PTRACE_SETFPREGS          15
 
 #ifdef __KERNEL__
+#define __ARCH_SYS_PTRACE	1
 
 #ifndef PS_S
 #define PS_S  (0x2000)
include/asm-s390/ptrace.h +2 -0
Index: linux-2.6/include/asm-s390/ptrace.h
===================================================================
@@ -468,6 +468,8 @@
 };
 
 #ifdef __KERNEL__
+#define __ARCH_SYS_PTRACE	1
+
 #define user_mode(regs) (((regs)->psw.mask & PSW_MASK_PSTATE) != 0)
 #define instruction_pointer(regs) ((regs)->psw.addr & PSW_ADDR_INSN)
 #define profile_pc(regs) instruction_pointer(regs)
arch/ia64/ia32/sys_ia32.c +1 -0
Index: linux-2.6/arch/ia64/ia32/sys_ia32.c
===================================================================
@@ -50,6 +50,7 @@
 #include <linux/compat.h>
 #include <linux/vfs.h>
 #include <linux/mman.h>
+#include <linux/syscalls.h>
 
 #include <asm/intrinsics.h>
 #include <asm/semaphore.h>
include/linux/syscalls.h +4 -0
Index: linux-2.6/include/linux/syscalls.h
===================================================================
@@ -60,6 +60,7 @@
 #include <asm/semaphore.h>
 #include <asm/siginfo.h>
 #include <asm/signal.h>
+#include <asm/ptrace.h> /* for __ARCH_SYS_PTRACE */
 #include <linux/quota.h>
 #include <linux/key.h>
 
@@ -477,6 +478,9 @@
 				unsigned long off, unsigned long len,
 				void __user *buf);
 
+#ifndef __ARCH_SYS_PTRACE
+asmlinkage long sys_ptrace(long request, long pid, long addr, long data);
+#endif
 asmlinkage long sys_prctl(int option, unsigned long arg2, unsigned long arg3,
 			unsigned long arg4, unsigned long arg5);
 asmlinkage long sys_swapon(const char __user *specialfile, int swap_flags);