consolidate sys_ptrace
Subsystems (9)
PATCH 1/1 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: alpha, ia64, m32r, parisc, sparc, sparc64. 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.
Only tested on ppc32 so far.
arch/arm/kernel/ptrace.c +1 -48
@@ -648,7 +648,7 @@#endif -static int do_ptrace (int request,struct task_struct *child,long addr,long data) +int 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
@@ -57,43 +57,10 @@h8300_disable_trace (child); } -asmlinkage int sys_ptrace(long request, long pid, long addr, long data) +int 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/m68k/kernel/ptrace.c +2 -39
56 lines not on this page · raw message
arch/m68knommu/kernel/ptrace.c +1 -38
@@ -101,43 +101,10 @@put_reg (child,PT_SR , tmp); } -asmlinkage int sys_ptrace(long request, long pid, long addr, long data) +int 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/s390/kernel/ptrace.c +1 -44
57 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 +69 -0
72 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
@@ -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
@@ -537,7 +537,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
@@ -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
@@ -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
@@ -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
@@ -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
@@ -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
@@ -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-m68k/unistd.h +0 -1
@@ -444,7 +444,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 ;struct sigaction ; asmlinkage long sys_rt_sigaction(int sig,
include/asm-m68knommu/unistd.h +0 -1
@@ -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
@@ -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
@@ -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
@@ -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
@@ -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-s390/unistd.h +0 -1
@@ -590,7 +590,6 @@asmlinkage long sys_fork (struct pt_regs regs);asmlinkage long sys_vfork (struct pt_regs regs);asmlinkage long sys_pipe (unsigned long __user *fildes); -asmlinkage long 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-sh/unistd.h +0 -1
@@ -497,7 +497,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
@@ -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
@@ -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
@@ -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
@@ -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
@@ -76,6 +76,8 @@#include <linux/compiler.h> /* For unlikely. */ #include <linux/sched.h> /* For struct task_struct. */ + +extern int 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 +26 -56
100 lines not on this page · raw message
arch/sh64/kernel/syscalls.S +1 -1
@@ -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
Christoph Hellwig <[email protected]> wrote on 08/10/2005 10:00:57 AM:
Quoted 11 lines
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.Some architectures have a too different ptrace so we have to exclude
them: alpha, ia64, m32r, parisc, sparc, sparc64. They continue to keep their implementations. For sh64 I had to add ash64_ptracewrapper because it does some initialization on the first call. For um I removed an ifdefedSUBARCH_PTRACE_SPECIALblock, butSUBARCH_PTRACE_SPECIALisn't defined anywhere in the tree.
There is one small problem with the new ptrace code for s390. We have this horribly broken ptrace hack to get the ieee instruction pointer of the last fpu exception. The fpu itself doesn't store the value so the exception handler of the kernel stores the instruction pointer to the thread structure. A process is allowed to ptrace itself (!) with the peek/poke value of PT_IEEE_IP to get this value. This is used in the fpu code in glibc. I know this is broken but I can't help it. Without this hack existing glibc code will fall over.
To make this work the special case needs to be dealt with before the ptrace_check_attach check is done. My suggestion would be to move the ptrace_check_attach to the arch_ptrace function. Then the s390 specific arch_ptrace function could insert the PT_IEEE_IP check before calling ptrace_chek_attach. The only other alternative is a s390 copy of sys_ptrace.
blue skies,
Martin
Martin Schwidefsky
Linux for zSeries Development & Services
IBM Deutschland Entwicklung GmbH
Quoted 23 lines · Martin Schwidefsky
Christoph Hellwig <[email protected]> wrote on 08/10/2005 10:00:57 AM:
Quoted 11 lines
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.Some architectures have a too different ptrace so we have to exclude
them: alpha, ia64, m32r, parisc, sparc, sparc64. They continue to keep their implementations. For sh64 I had to add ash64_ptracewrapper because it does some initialization on the first call. For um I removed an ifdefedSUBARCH_PTRACE_SPECIALblock, butSUBARCH_PTRACE_SPECIALisn't defined anywhere in the tree.There is one small problem with the new ptrace code for s390. We have this horribly broken ptrace hack to get the ieee instruction pointer of the last fpu exception. The fpu itself doesn't store the value so the exception handler of the kernel stores the instruction pointer to the thread structure. A process is allowed to ptrace itself (!) with the peek/poke value of
PT_IEEE_IPto get this value. This is used in the fpu code in glibc. I know this is broken but I can't help it. Without this hack existing glibc code will fall over.
Quoted 6 lines
To make this work the special case needs to be dealt with before the
ptrace_check_attachcheck is done. My suggestion would be to move theptrace_check_attachto thearch_ptracefunction. Then the s390 specificarch_ptracefunction could insert thePT_IEEE_IPcheck before callingptrace_chek_attach. The only other alternative is a s390 copy ofsys_ptrace.
I suspect at this point it's better to leave s390 out of the consolidation. I'll have another patch that'll make the implementations that aren't consolidated use the new ptrace_get_task_struct function, so there will be far less code duplicated than now.
x86-64 part is ok for me.
-Andi
Quoted 4 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.
Looks okay for FRV.
My biggest concern with doing things like this is that it eats away at the kernel stack space available for a syscall, though I don't think it'll be too much of a problem in this case.
Is there also a way to get rid of the lock_kernel() call?
David
Quoted 6 lines · Christoph Hellwig
Some architectures have a too different ptrace so we have to exclude
them: alpha, ia64, m32r, parisc, sparc, sparc64. They continue to keep their implementations. For sh64 I had to add ash64_ptracewrapper because it does some initialization on the first call. For um I removed an ifdefedSUBARCH_PTRACE_SPECIALblock, butSUBARCH_PTRACE_SPECIALisn't defined anywhere in the tree.
Looks ok for sh and sh64.
Quoted 5 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.
Quoted 8 lines
Some architectures have a too different ptrace so we have to exclude
them: alpha, ia64, m32r, parisc, sparc, sparc64. They continue to keep their implementations. For sh64 I had to add ash64_ptracewrapper because it does some initialization on the first call. For um I removed an ifdefedSUBARCH_PTRACE_SPECIALblock, butSUBARCH_PTRACE_SPECIALisn't defined anywhere in the tree.Only tested on ppc32 so far.
MIPS bits looking good.
Ralf
Quoted 4 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.
OK for UML.
Jeff
Quoted 2 lines · Christoph Hellwig
Some architectures have a too different ptrace so we have to exclude
them: alpha...
Alpha could be updated to use this, I think. Just a matter of using force_successful_syscall_return instead of pt_regs directly.
I'll have a look at testing this.
r~
Hi,
Quoted 4 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.
No objection really, but I recently reformatted the m68k sys_ptrace() so it would be easier to regenerate your changes on top of this. I can do this for you if we can agree on to merge at least the m68k ptrace changes before this.
For reference I put the patches at www.xs4all.nl/~zippel/m68k_merge/ (tf, p_ws, p_c are the relevant patches).
Al, this also includes the updated thread_info patches, I fixed some of m68k specific parts. Could you please expand a little on the objections you made on IRC?
bye, Roman
Quoted 6 lines · Roman Zippel
No objection really, but I recently reformatted the m68k
sys_ptrace()so it would be easier to regenerate your changes on top of this. I can do this for you if we can agree on to merge at least the m68k ptrace changes before this.
For reference I put the patches at www.xs4all.nl/~zippel/m68k_merge/ (tf,p_ws,p_care the relevant patches).
I'll leave m68k out of the patchset for now. If you have your patches done when I'm doing the next round of changes in I'll do it atop of those, else you'll have to redo your changes, bad luck for not syncing up with mainline.
Quoted 1 line · Christoph Hellwig
Signed-off-by Christoph Hellwig <[email protected]>
Thanks Christoph.
Signature · 3 lines
Russell King Linux kernel 2.6 ARM Linux - http://www.arm.linux.org.uk/ maintainer of: 2.6 Serial core
Quoted 4 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.
The signature of arch_ptrace needs to return long, and not int. The PTRACE_PEEK{TEXT,DATA,USR} requests return a "word", which on 64-bit arches needs to be a 64-bit type.
r~
Quoted 9 lines · Richard Henderson
Quoted 4 lines · Christoph Hellwig
The
sys_ptraceboilerplate code (everything outside the big switch statement for the arch-specific requests) is shared by most architectures. This patch moves it tokernel/ptrace.cand leaves the arch-specific code asarch_ptrace.The signature of
arch_ptraceneeds to return long, and not int. The PTRACE_PEEK{TEXT,DATA,USR} requests return a "word", which on 64-bit arches needs to be a 64-bit type.
Ok. Will be that way in the next patch.