1 /**********************************************************************
4 Copyright (C) 1999 Lars Brinkhoff. See the file COPYING for licensing
7 Jeff Dike (jdike@karaya.com) : Modified for integration into uml
8 **********************************************************************/
13 #include <sys/types.h>
19 #include "kern_util.h"
20 #include "ptrace_user.h"
24 long proxy_ptrace(struct debugger *debugger, int arg1, pid_t arg2,
25 long arg3, long arg4, pid_t child, int *ret)
32 if(debugger->debugee->died) return(-ESRCH);
36 if(debugger->debugee->traced) return(-EPERM);
38 debugger->debugee->pid = arg2;
39 debugger->debugee->traced = 1;
41 if(is_valid_pid(arg2) && (arg2 != child)){
42 debugger->debugee->in_context = 0;
44 debugger->debugee->event = 1;
45 debugger->debugee->wait_status = W_STOPCODE(SIGSTOP);
48 debugger->debugee->in_context = 1;
49 if(debugger->debugee->stopped)
50 child_proxy(child, W_STOPCODE(SIGSTOP));
51 else kill(child, SIGSTOP);
57 if(!debugger->debugee->traced) return(-EPERM);
59 debugger->debugee->traced = 0;
60 debugger->debugee->pid = 0;
61 if(!debugger->debugee->in_context)
67 if(!debugger->debugee->in_context) return(-EPERM);
69 return(ptrace(PTRACE_CONT, child, arg3, arg4));
71 #ifdef UM_HAVE_GETFPREGS
72 case PTRACE_GETFPREGS:
74 long regs[FP_FRAME_SIZE];
77 result = ptrace(PTRACE_GETFPREGS, child, 0, regs);
78 if(result == -1) return(-errno);
80 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
81 ptrace(PTRACE_POKEDATA, debugger->pid, arg4 + 4 * i,
87 #ifdef UM_HAVE_GETFPXREGS
88 case PTRACE_GETFPXREGS:
90 long regs[FPX_FRAME_SIZE];
93 result = ptrace(PTRACE_GETFPXREGS, child, 0, regs);
94 if(result == -1) return(-errno);
96 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
97 ptrace(PTRACE_POKEDATA, debugger->pid, arg4 + 4 * i,
103 #ifdef UM_HAVE_GETREGS
106 long regs[FRAME_SIZE];
109 result = ptrace(PTRACE_GETREGS, child, 0, regs);
110 if(result == -1) return(-errno);
112 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
113 ptrace (PTRACE_POKEDATA, debugger->pid,
114 arg4 + 4 * i, regs[i]);
121 result = ptrace(PTRACE_KILL, child, arg3, arg4);
122 if(result == -1) return(-errno);
126 case PTRACE_PEEKDATA:
127 case PTRACE_PEEKTEXT:
129 /* The value being read out could be -1, so we have to
130 * check errno to see if there's an error, and zero it
131 * beforehand so we're not faked out by an old error
135 result = ptrace(arg1, child, arg3, 0);
136 if((result == -1) && (errno != 0)) return(-errno);
138 result = ptrace(PTRACE_POKEDATA, debugger->pid, arg4, result);
139 if(result == -1) return(-errno);
143 case PTRACE_POKEDATA:
144 case PTRACE_POKETEXT:
146 result = ptrace(arg1, child, arg3, arg4);
147 if(result == -1) return(-errno);
149 if(arg1 == PTRACE_POKEUSR) ptrace_pokeuser(arg3, arg4);
152 #ifdef UM_HAVE_SETFPREGS
153 case PTRACE_SETFPREGS:
155 long regs[FP_FRAME_SIZE];
158 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
159 regs[i] = ptrace (PTRACE_PEEKDATA, debugger->pid,
161 result = ptrace(PTRACE_SETFPREGS, child, 0, regs);
162 if(result == -1) return(-errno);
168 #ifdef UM_HAVE_SETFPXREGS
169 case PTRACE_SETFPXREGS:
171 long regs[FPX_FRAME_SIZE];
174 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
175 regs[i] = ptrace (PTRACE_PEEKDATA, debugger->pid,
177 result = ptrace(PTRACE_SETFPXREGS, child, 0, regs);
178 if(result == -1) return(-errno);
184 #ifdef UM_HAVE_SETREGS
187 long regs[FRAME_SIZE];
190 for (i = 0; i < sizeof(regs)/sizeof(regs[0]); i++)
191 regs[i] = ptrace(PTRACE_PEEKDATA, debugger->pid,
193 result = ptrace(PTRACE_SETREGS, child, 0, regs);
194 if(result == -1) return(-errno);
200 case PTRACE_SINGLESTEP:
201 if(!debugger->debugee->in_context) return(-EPERM);
203 sigaddset(&relay, SIGSEGV);
204 sigaddset(&relay, SIGILL);
205 sigaddset(&relay, SIGBUS);
206 result = ptrace(PTRACE_SINGLESTEP, child, arg3, arg4);
207 if(result == -1) return(-errno);
209 status = wait_for_stop(child, SIGTRAP, PTRACE_SINGLESTEP,
211 child_proxy(child, status);
215 if(!debugger->debugee->in_context) return(-EPERM);
216 result = ptrace(PTRACE_SYSCALL, child, arg3, arg4);
217 if(result == -1) return(-errno);
219 *ret = PTRACE_SYSCALL;
229 * Overrides for Emacs so that we follow Linus's tabbing style.
230 * Emacs will notice this stuff at the end of the file and automatically
231 * adjust the settings for this buffer only. This must remain at the end
233 * ---------------------------------------------------------------------------
235 * c-file-style: "linux"