blob: bd806674e0825ddd5dfed766e4da4f1e87421cc9 [file] [log] [blame]
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001/*
2 * Copyright (c) 1991, 1992 Paul Kranenburg <pk@cs.few.eur.nl>
3 * Copyright (c) 1993 Branko Lankester <branko@hacktic.nl>
4 * Copyright (c) 1993, 1994, 1995, 1996 Rick Sladkey <jrs@world.std.com>
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00005 * Copyright (c) 1996-1999 Wichert Akkerman <wichert@cistron.nl>
6 * Copyright (c) 1999 IBM Deutschland Entwicklung GmbH, IBM Corporation
7 * Linux for s390 port by D.J. Barrow
8 * <barrow_dj@mail.yahoo.com,djbarrow@de.ibm.com>
Wichert Akkermanccef6372002-05-01 16:39:22 +00009 * Copyright (c) 2000 PocketPenguins Inc. Linux for Hitachi SuperH
10 * port by Greg Banks <gbanks@pocketpenguins.com>
11
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +000012 *
Wichert Akkerman76baf7c1999-02-19 00:21:36 +000013 * All rights reserved.
14 *
15 * Redistribution and use in source and binary forms, with or without
16 * modification, are permitted provided that the following conditions
17 * are met:
18 * 1. Redistributions of source code must retain the above copyright
19 * notice, this list of conditions and the following disclaimer.
20 * 2. Redistributions in binary form must reproduce the above copyright
21 * notice, this list of conditions and the following disclaimer in the
22 * documentation and/or other materials provided with the distribution.
23 * 3. The name of the author may not be used to endorse or promote products
24 * derived from this software without specific prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
27 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
28 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
29 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
30 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
31 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
35 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36 *
37 * $Id$
38 */
39
40#include "defs.h"
41
42#include <fcntl.h>
43#include <sys/stat.h>
44#include <sys/time.h>
45#include <sys/wait.h>
46#include <sys/resource.h>
47#include <sys/utsname.h>
48#include <sys/user.h>
49#include <sys/syscall.h>
50#include <signal.h>
51#ifdef SUNOS4
52#include <machine/reg.h>
53#endif /* SUNOS4 */
54
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +000055#ifdef FREEBSD
56#include <sys/ptrace.h>
57#endif
58
Wichert Akkerman00a82ee2001-03-28 20:29:17 +000059#if HAVE_ASM_REG_H
Roland McGrath6d1a65c2004-07-12 07:44:08 +000060#if defined (SPARC) || defined (SPARC64)
Wichert Akkerman00a82ee2001-03-28 20:29:17 +000061# define fpq kernel_fpq
62# define fq kernel_fq
63# define fpu kernel_fpu
Roland McGrath6d1a65c2004-07-12 07:44:08 +000064#endif /* SPARC || SPARC64 */
Wichert Akkerman00a82ee2001-03-28 20:29:17 +000065#include <asm/reg.h>
Roland McGrath6d1a65c2004-07-12 07:44:08 +000066#if defined (SPARC) || defined (SPARC64)
Wichert Akkerman00a82ee2001-03-28 20:29:17 +000067# undef fpq
68# undef fq
Roland McGrath5a223472002-12-15 23:58:26 +000069# undef fpu
Roland McGrath6d1a65c2004-07-12 07:44:08 +000070#endif /* SPARC || SPARC64 */
Wichert Akkerman00a82ee2001-03-28 20:29:17 +000071#endif /* HAVE_ASM_REG_H */
72
Wichert Akkerman36915a11999-07-13 15:45:02 +000073#ifdef HAVE_SYS_REG_H
Wichert Akkerman76baf7c1999-02-19 00:21:36 +000074# include <sys/reg.h>
Wichert Akkerman15dea971999-10-06 13:06:34 +000075#ifndef PTRACE_PEEKUSR
Wichert Akkerman76baf7c1999-02-19 00:21:36 +000076# define PTRACE_PEEKUSR PTRACE_PEEKUSER
Wichert Akkerman15dea971999-10-06 13:06:34 +000077#endif
78#ifndef PTRACE_POKEUSR
Wichert Akkerman76baf7c1999-02-19 00:21:36 +000079# define PTRACE_POKEUSR PTRACE_POKEUSER
80#endif
Wichert Akkerman15dea971999-10-06 13:06:34 +000081#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +000082
Roland McGrath5bd7cf82003-01-24 04:31:18 +000083#ifdef HAVE_LINUX_PTRACE_H
84#undef PTRACE_SYSCALL
Roland McGrathfb1bc072004-03-01 21:29:24 +000085# ifdef HAVE_STRUCT_IA64_FPREG
86# define ia64_fpreg XXX_ia64_fpreg
87# endif
88# ifdef HAVE_STRUCT_PT_ALL_USER_REGS
89# define pt_all_user_regs XXX_pt_all_user_regs
90# endif
Roland McGrath5bd7cf82003-01-24 04:31:18 +000091#include <linux/ptrace.h>
Roland McGrathfb1bc072004-03-01 21:29:24 +000092# undef ia64_fpreg
93# undef pt_all_user_regs
Roland McGrath5bd7cf82003-01-24 04:31:18 +000094#endif
95
Roland McGrath6d1a65c2004-07-12 07:44:08 +000096#if defined (LINUX) && defined (SPARC64)
97# define r_pc r_tpc
98# undef PTRACE_GETREGS
99# define PTRACE_GETREGS PTRACE_GETREGS64
100# undef PTRACE_SETREGS
101# define PTRACE_SETREGS PTRACE_SETREGS64
102#endif /* LINUX && SPARC64 */
103
Roland McGrath5a223472002-12-15 23:58:26 +0000104#ifdef HAVE_LINUX_FUTEX_H
105#include <linux/futex.h>
106#endif
107#if defined LINUX
108# ifndef FUTEX_WAIT
109# define FUTEX_WAIT 0
110# endif
111# ifndef FUTEX_WAKE
112# define FUTEX_WAKE 1
113# endif
114# ifndef FUTEX_FD
115# define FUTEX_FD 2
116# endif
Roland McGrath88812d62003-06-26 22:27:23 +0000117# ifndef FUTEX_REQUEUE
118# define FUTEX_REQUEUE 3
119# endif
Roland McGrath5a223472002-12-15 23:58:26 +0000120#endif
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000121
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000122#ifdef LINUX
Roland McGrath279d3782004-03-01 20:27:37 +0000123#include <sched.h>
Wichert Akkerman2e2553a1999-05-09 00:29:58 +0000124#include <asm/posix_types.h>
125#undef GETGROUPS_T
126#define GETGROUPS_T __kernel_gid_t
Roland McGrath83bd47a2003-11-13 22:32:26 +0000127#undef GETGROUPS32_T
128#define GETGROUPS32_T __kernel_gid32_t
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000129#endif /* LINUX */
130
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000131#if defined(LINUX) && defined(IA64)
132# include <asm/ptrace_offsets.h>
133# include <asm/rse.h>
134#endif
135
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000136#ifdef HAVE_PRCTL
137#include <sys/prctl.h>
138#endif
139
140#ifndef WCOREDUMP
141#define WCOREDUMP(status) ((status) & 0200)
142#endif
143
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000144/* WTA: this was `&& !defined(LINUXSPARC)', this seems unneeded though? */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000145#if defined(HAVE_PRCTL)
Roland McGrathd9f816f2004-09-04 03:39:20 +0000146static const struct xlat prctl_options[] = {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000147#ifdef PR_MAXPROCS
148 { PR_MAXPROCS, "PR_MAXPROCS" },
149#endif
150#ifdef PR_ISBLOCKED
151 { PR_ISBLOCKED, "PR_ISBLOCKED" },
152#endif
153#ifdef PR_SETSTACKSIZE
154 { PR_SETSTACKSIZE, "PR_SETSTACKSIZE" },
155#endif
156#ifdef PR_GETSTACKSIZE
157 { PR_GETSTACKSIZE, "PR_GETSTACKSIZE" },
158#endif
159#ifdef PR_MAXPPROCS
160 { PR_MAXPPROCS, "PR_MAXPPROCS" },
161#endif
162#ifdef PR_UNBLKONEXEC
163 { PR_UNBLKONEXEC, "PR_UNBLKONEXEC" },
164#endif
165#ifdef PR_ATOMICSIM
166 { PR_ATOMICSIM, "PR_ATOMICSIM" },
167#endif
168#ifdef PR_SETEXITSIG
169 { PR_SETEXITSIG, "PR_SETEXITSIG" },
170#endif
171#ifdef PR_RESIDENT
172 { PR_RESIDENT, "PR_RESIDENT" },
173#endif
174#ifdef PR_ATTACHADDR
175 { PR_ATTACHADDR, "PR_ATTACHADDR" },
176#endif
177#ifdef PR_DETACHADDR
178 { PR_DETACHADDR, "PR_DETACHADDR" },
179#endif
180#ifdef PR_TERMCHILD
181 { PR_TERMCHILD, "PR_TERMCHILD" },
182#endif
183#ifdef PR_GETSHMASK
184 { PR_GETSHMASK, "PR_GETSHMASK" },
185#endif
186#ifdef PR_GETNSHARE
187 { PR_GETNSHARE, "PR_GETNSHARE" },
188#endif
Wichert Akkerman8829a551999-06-11 13:18:40 +0000189#ifdef PR_COREPID
190 { PR_COREPID, "PR_COREPID" },
191#endif
192#ifdef PR_ATTACHADDRPERM
193 { PR_ATTACHADDRPERM, "PR_ATTACHADDRPERM" },
194#endif
195#ifdef PR_PTHREADEXIT
196 { PR_PTHREADEXIT, "PR_PTHREADEXIT" },
197#endif
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +0000198#ifdef PR_SET_PDEATHSIG
199 { PR_SET_PDEATHSIG, "PR_SET_PDEATHSIG" },
200#endif
201#ifdef PR_GET_PDEATHSIG
202 { PR_GET_PDEATHSIG, "PR_GET_PDEATHSIG" },
203#endif
Dmitry V. Levinf02cf212008-09-03 00:54:40 +0000204#ifdef PR_GET_DUMPABLE
205 { PR_GET_DUMPABLE, "PR_GET_DUMPABLE" },
206#endif
207#ifdef PR_SET_DUMPABLE
208 { PR_SET_DUMPABLE, "PR_SET_DUMPABLE" },
209#endif
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000210#ifdef PR_GET_UNALIGN
211 { PR_GET_UNALIGN, "PR_GET_UNALIGN" },
212#endif
213#ifdef PR_SET_UNALIGN
214 { PR_SET_UNALIGN, "PR_SET_UNALIGN" },
215#endif
216#ifdef PR_GET_KEEPCAPS
Dmitry V. Levin8dd31dd2008-11-11 00:25:22 +0000217 { PR_GET_KEEPCAPS, "PR_GET_KEEPCAPS" },
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000218#endif
219#ifdef PR_SET_KEEPCAPS
Dmitry V. Levin8dd31dd2008-11-11 00:25:22 +0000220 { PR_SET_KEEPCAPS, "PR_SET_KEEPCAPS" },
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000221#endif
Roland McGrathe5039fb2007-11-03 23:58:07 +0000222#ifdef PR_GET_FPEMU
223 { PR_GET_FPEMU, "PR_GET_FPEMU" },
224#endif
225#ifdef PR_SET_FPEMU
226 { PR_SET_FPEMU, "PR_SET_FPEMU" },
227#endif
228#ifdef PR_GET_FPEXC
229 { PR_GET_FPEXC, "PR_GET_FPEXC" },
230#endif
231#ifdef PR_SET_FPEXC
232 { PR_SET_FPEXC, "PR_SET_FPEXC" },
233#endif
234#ifdef PR_GET_TIMING
235 { PR_GET_TIMING, "PR_GET_TIMING" },
236#endif
237#ifdef PR_SET_TIMING
238 { PR_SET_TIMING, "PR_SET_TIMING" },
239#endif
240#ifdef PR_SET_NAME
241 { PR_SET_NAME, "PR_SET_NAME" },
242#endif
243#ifdef PR_GET_NAME
244 { PR_GET_NAME, "PR_GET_NAME" },
245#endif
246#ifdef PR_GET_ENDIAN
247 { PR_GET_ENDIAN, "PR_GET_ENDIAN" },
248#endif
249#ifdef PR_SET_ENDIAN
250 { PR_SET_ENDIAN, "PR_SET_ENDIAN" },
251#endif
252#ifdef PR_GET_SECCOMP
253 { PR_GET_SECCOMP, "PR_GET_SECCOMP" },
254#endif
255#ifdef PR_SET_SECCOMP
256 { PR_SET_SECCOMP, "PR_SET_SECCOMP" },
257#endif
Dmitry V. Levin8dd31dd2008-11-11 00:25:22 +0000258#ifdef PR_GET_TSC
259 { PR_GET_TSC, "PR_GET_TSC" },
260#endif
261#ifdef PR_SET_TSC
262 { PR_SET_TSC, "PR_SET_TSC" },
263#endif
264#ifdef PR_GET_SECUREBITS
265 { PR_GET_SECUREBITS, "PR_GET_SECUREBITS" },
266#endif
267#ifdef PR_SET_SECUREBITS
268 { PR_SET_SECUREBITS, "PR_SET_SECUREBITS" },
269#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000270 { 0, NULL },
271};
272
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000273
Roland McGratha4d48532005-06-08 20:45:28 +0000274static const char *
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000275unalignctl_string (unsigned int ctl)
276{
277 static char buf[16];
278
279 switch (ctl) {
280#ifdef PR_UNALIGN_NOPRINT
281 case PR_UNALIGN_NOPRINT:
282 return "NOPRINT";
283#endif
284#ifdef PR_UNALIGN_SIGBUS
285 case PR_UNALIGN_SIGBUS:
286 return "SIGBUS";
287#endif
288 default:
289 break;
290 }
291 sprintf(buf, "%x", ctl);
292 return buf;
293}
294
295
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000296int
297sys_prctl(tcp)
298struct tcb *tcp;
299{
300 int i;
301
302 if (entering(tcp)) {
303 printxval(prctl_options, tcp->u_arg[0], "PR_???");
304 switch (tcp->u_arg[0]) {
305#ifdef PR_GETNSHARE
306 case PR_GETNSHARE:
307 break;
308#endif
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000309#ifdef PR_SET_PDEATHSIG
310 case PR_SET_PDEATHSIG:
311 tprintf(", %lu", tcp->u_arg[1]);
312 break;
313#endif
314#ifdef PR_GET_PDEATHSIG
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +0000315 case PR_GET_PDEATHSIG:
316 break;
317#endif
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000318#ifdef PR_SET_DUMPABLE
319 case PR_SET_DUMPABLE:
320 tprintf(", %lu", tcp->u_arg[1]);
321 break;
322#endif
323#ifdef PR_GET_DUMPABLE
324 case PR_GET_DUMPABLE:
325 break;
326#endif
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000327#ifdef PR_SET_UNALIGN
328 case PR_SET_UNALIGN:
329 tprintf(", %s", unalignctl_string(tcp->u_arg[1]));
330 break;
331#endif
332#ifdef PR_GET_UNALIGN
333 case PR_GET_UNALIGN:
334 tprintf(", %#lx", tcp->u_arg[1]);
335 break;
336#endif
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000337#ifdef PR_SET_KEEPCAPS
338 case PR_SET_KEEPCAPS:
339 tprintf(", %lu", tcp->u_arg[1]);
340 break;
341#endif
342#ifdef PR_GET_KEEPCAPS
343 case PR_GET_KEEPCAPS:
344 break;
345#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000346 default:
347 for (i = 1; i < tcp->u_nargs; i++)
348 tprintf(", %#lx", tcp->u_arg[i]);
349 break;
350 }
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +0000351 } else {
352 switch (tcp->u_arg[0]) {
353#ifdef PR_GET_PDEATHSIG
354 case PR_GET_PDEATHSIG:
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000355 if (umove(tcp, tcp->u_arg[1], &i) < 0)
356 tprintf(", %#lx", tcp->u_arg[1]);
357 else
358 tprintf(", {%u}", i);
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +0000359 break;
360#endif
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000361#ifdef PR_GET_DUMPABLE
362 case PR_GET_DUMPABLE:
363 return RVAL_UDECIMAL;
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000364#endif
365#ifdef PR_GET_UNALIGN
366 case PR_GET_UNALIGN:
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000367 if (syserror(tcp) || umove(tcp, tcp->u_arg[1], &i) < 0)
368 break;
369 tcp->auxstr = unalignctl_string(i);
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000370 return RVAL_STR;
Dmitry V. Levin50f60132008-09-03 00:56:52 +0000371#endif
372#ifdef PR_GET_KEEPCAPS
373 case PR_GET_KEEPCAPS:
374 return RVAL_UDECIMAL;
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000375#endif
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +0000376 default:
377 break;
378 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000379 }
380 return 0;
381}
382
383#endif /* HAVE_PRCTL */
384
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +0000385#if defined(FREEBSD) || defined(SUNOS4) || defined(SVR4)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000386int
387sys_gethostid(tcp)
388struct tcb *tcp;
389{
390 if (exiting(tcp))
391 return RVAL_HEX;
392 return 0;
393}
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +0000394#endif /* FREEBSD || SUNOS4 || SVR4 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000395
396int
397sys_sethostname(tcp)
398struct tcb *tcp;
399{
400 if (entering(tcp)) {
401 printpathn(tcp, tcp->u_arg[0], tcp->u_arg[1]);
402 tprintf(", %lu", tcp->u_arg[1]);
403 }
404 return 0;
405}
406
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +0000407#if defined(ALPHA) || defined(FREEBSD) || defined(SUNOS4) || defined(SVR4)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000408int
409sys_gethostname(tcp)
410struct tcb *tcp;
411{
412 if (exiting(tcp)) {
413 if (syserror(tcp))
414 tprintf("%#lx", tcp->u_arg[0]);
415 else
416 printpath(tcp, tcp->u_arg[0]);
417 tprintf(", %lu", tcp->u_arg[1]);
418 }
419 return 0;
420}
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +0000421#endif /* ALPHA || FREEBSD || SUNOS4 || SVR4 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000422
423int
424sys_setdomainname(tcp)
425struct tcb *tcp;
426{
427 if (entering(tcp)) {
428 printpathn(tcp, tcp->u_arg[0], tcp->u_arg[1]);
429 tprintf(", %lu", tcp->u_arg[1]);
430 }
431 return 0;
432}
433
Wichert Akkerman5daa0281999-03-15 19:49:42 +0000434#if !defined(LINUX)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000435
436int
437sys_getdomainname(tcp)
438struct tcb *tcp;
439{
440 if (exiting(tcp)) {
441 if (syserror(tcp))
442 tprintf("%#lx", tcp->u_arg[0]);
443 else
444 printpath(tcp, tcp->u_arg[0]);
445 tprintf(", %lu", tcp->u_arg[1]);
446 }
447 return 0;
448}
449#endif /* !LINUX */
450
451int
452sys_exit(tcp)
453struct tcb *tcp;
454{
455 if (exiting(tcp)) {
456 fprintf(stderr, "_exit returned!\n");
457 return -1;
458 }
459 /* special case: we stop tracing this process, finish line now */
460 tprintf("%ld) ", tcp->u_arg[0]);
461 tabto(acolumn);
462 tprintf("= ?");
Denys Vlasenkoef2fbf82009-01-06 21:45:06 +0000463 printtrailer();
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000464 return 0;
465}
466
467int
468internal_exit(tcp)
469struct tcb *tcp;
470{
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000471 if (entering(tcp)) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000472 tcp->flags |= TCB_EXITING;
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000473#ifdef __NR_exit_group
Roland McGrath08267b82004-02-20 22:56:43 +0000474# ifdef IA64
475 if (ia32) {
476 if (tcp->scno == 252)
477 tcp->flags |= TCB_GROUP_EXITING;
478 } else
479# endif
Roland McGratha4f9f2d2005-06-07 23:21:20 +0000480 if (known_scno(tcp) == __NR_exit_group)
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000481 tcp->flags |= TCB_GROUP_EXITING;
482#endif
483 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000484 return 0;
485}
486
Roland McGrathee9d4352002-12-18 04:16:10 +0000487/* TCP is creating a child we want to follow.
488 If there will be space in tcbtab for it, set TCB_FOLLOWFORK and return 0.
489 If not, clear TCB_FOLLOWFORK, print an error, and return 1. */
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000490static void
Roland McGrathee9d4352002-12-18 04:16:10 +0000491fork_tcb(struct tcb *tcp)
492{
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000493 if (nprocs == tcbtabsize)
494 expand_tcbtab();
Roland McGrathee9d4352002-12-18 04:16:10 +0000495
496 tcp->flags |= TCB_FOLLOWFORK;
Roland McGrathee9d4352002-12-18 04:16:10 +0000497}
498
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +0000499#ifdef USE_PROCFS
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000500
501int
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000502sys_fork(struct tcb *tcp)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000503{
Dmitry V. Levin21a75342008-09-03 01:22:18 +0000504 if (exiting(tcp) && !syserror(tcp)) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000505 if (getrval2(tcp)) {
506 tcp->auxstr = "child process";
507 return RVAL_UDECIMAL | RVAL_STR;
508 }
509 }
510 return 0;
511}
512
John Hughes4e36a812001-04-18 15:11:51 +0000513#if UNIXWARE > 2
514
515int
516sys_rfork(tcp)
517struct tcb *tcp;
518{
519 if (entering(tcp)) {
520 tprintf ("%ld", tcp->u_arg[0]);
521 }
Dmitry V. Levin21a75342008-09-03 01:22:18 +0000522 else if (!syserror(tcp)) {
John Hughes4e36a812001-04-18 15:11:51 +0000523 if (getrval2(tcp)) {
524 tcp->auxstr = "child process";
525 return RVAL_UDECIMAL | RVAL_STR;
526 }
527 }
528 return 0;
529}
530
531#endif
532
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000533int
534internal_fork(tcp)
535struct tcb *tcp;
536{
537 struct tcb *tcpchild;
538
539 if (exiting(tcp)) {
Roland McGrathf3a0e1b2003-02-20 02:45:22 +0000540#ifdef SYS_rfork
Roland McGratha4f9f2d2005-06-07 23:21:20 +0000541 if (known_scno(tcp) == SYS_rfork && !(tcp->u_arg[0]&RFPROC))
Roland McGrathf3a0e1b2003-02-20 02:45:22 +0000542 return 0;
543#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000544 if (getrval2(tcp))
545 return 0;
546 if (!followfork)
547 return 0;
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000548 fork_tcb(tcp);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000549 if (syserror(tcp))
550 return 0;
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000551 tcpchild = alloctcb(tcp->u_rval);
Wichert Akkerman2e4ffe52000-09-03 23:57:48 +0000552 if (proc_open(tcpchild, 2) < 0)
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +0000553 droptcb(tcpchild);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000554 }
555 return 0;
556}
557
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +0000558#else /* !USE_PROCFS */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000559
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000560#ifdef LINUX
561
562/* defines copied from linux/sched.h since we can't include that
563 * ourselves (it conflicts with *lots* of libc includes)
564 */
565#define CSIGNAL 0x000000ff /* signal mask to be sent at exit */
566#define CLONE_VM 0x00000100 /* set if VM shared between processes */
567#define CLONE_FS 0x00000200 /* set if fs info shared between processes */
568#define CLONE_FILES 0x00000400 /* set if open files shared between processes */
569#define CLONE_SIGHAND 0x00000800 /* set if signal handlers shared */
Roland McGrath909875b2002-12-22 03:34:36 +0000570#define CLONE_IDLETASK 0x00001000 /* kernel-only flag */
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000571#define CLONE_PTRACE 0x00002000 /* set if we want to let tracing continue on the child too */
572#define CLONE_VFORK 0x00004000 /* set if the parent wants the child to wake it up on mm_release */
573#define CLONE_PARENT 0x00008000 /* set if we want to have the same parent as the cloner */
Roland McGrath909875b2002-12-22 03:34:36 +0000574#define CLONE_THREAD 0x00010000 /* Same thread group? */
575#define CLONE_NEWNS 0x00020000 /* New namespace group? */
576#define CLONE_SYSVSEM 0x00040000 /* share system V SEM_UNDO semantics */
577#define CLONE_SETTLS 0x00080000 /* create a new TLS for the child */
578#define CLONE_PARENT_SETTID 0x00100000 /* set the TID in the parent */
579#define CLONE_CHILD_CLEARTID 0x00200000 /* clear the TID in the child */
580#define CLONE_DETACHED 0x00400000 /* parent wants no child-exit signal */
581#define CLONE_UNTRACED 0x00800000 /* set if the tracing process can't force CLONE_PTRACE on this clone */
582#define CLONE_CHILD_SETTID 0x01000000 /* set the TID in the child */
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000583
Roland McGrathd9f816f2004-09-04 03:39:20 +0000584static const struct xlat clone_flags[] = {
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000585 { CLONE_VM, "CLONE_VM" },
586 { CLONE_FS, "CLONE_FS" },
587 { CLONE_FILES, "CLONE_FILES" },
588 { CLONE_SIGHAND, "CLONE_SIGHAND" },
Roland McGrath909875b2002-12-22 03:34:36 +0000589 { CLONE_IDLETASK, "CLONE_IDLETASK"},
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000590 { CLONE_PTRACE, "CLONE_PTRACE" },
591 { CLONE_VFORK, "CLONE_VFORK" },
592 { CLONE_PARENT, "CLONE_PARENT" },
Roland McGrath909875b2002-12-22 03:34:36 +0000593 { CLONE_THREAD, "CLONE_THREAD" },
594 { CLONE_NEWNS, "CLONE_NEWNS" },
595 { CLONE_SYSVSEM, "CLONE_SYSVSEM" },
596 { CLONE_SETTLS, "CLONE_SETTLS" },
597 { CLONE_PARENT_SETTID,"CLONE_PARENT_SETTID" },
598 { CLONE_CHILD_CLEARTID,"CLONE_CHILD_CLEARTID" },
599 { CLONE_DETACHED, "CLONE_DETACHED" },
600 { CLONE_UNTRACED, "CLONE_UNTRACED" },
601 { CLONE_CHILD_SETTID,"CLONE_CHILD_SETTID" },
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000602 { 0, NULL },
603};
604
Roland McGrath909875b2002-12-22 03:34:36 +0000605# ifdef I386
606# include <asm/ldt.h>
Roland McGrath7decfb22004-03-01 22:10:52 +0000607# ifdef HAVE_STRUCT_USER_DESC
608# define modify_ldt_ldt_s user_desc
609# endif
Roland McGrath909875b2002-12-22 03:34:36 +0000610extern void print_ldt_entry();
611# endif
612
Roland McGrath9677b3a2003-03-12 09:54:36 +0000613# if defined IA64
614# define ARG_FLAGS 0
615# define ARG_STACK 1
Roland McGratha4f9f2d2005-06-07 23:21:20 +0000616# define ARG_STACKSIZE (known_scno(tcp) == SYS_clone2 ? 2 : -1)
617# define ARG_PTID (known_scno(tcp) == SYS_clone2 ? 3 : 2)
618# define ARG_CTID (known_scno(tcp) == SYS_clone2 ? 4 : 3)
619# define ARG_TLS (known_scno(tcp) == SYS_clone2 ? 5 : 4)
Roland McGrathfe5fdb22003-05-23 00:29:05 +0000620# elif defined S390 || defined S390X
Roland McGrath9677b3a2003-03-12 09:54:36 +0000621# define ARG_STACK 0
622# define ARG_FLAGS 1
623# define ARG_PTID 2
Roland McGrathfe5fdb22003-05-23 00:29:05 +0000624# define ARG_CTID 3
625# define ARG_TLS 4
Roland McGrath9c555e72003-07-09 09:47:59 +0000626# elif defined X86_64 || defined ALPHA
Roland McGrath361aac52003-03-18 07:43:42 +0000627# define ARG_FLAGS 0
628# define ARG_STACK 1
629# define ARG_PTID 2
630# define ARG_CTID 3
631# define ARG_TLS 4
Roland McGrath9677b3a2003-03-12 09:54:36 +0000632# else
633# define ARG_FLAGS 0
634# define ARG_STACK 1
635# define ARG_PTID 2
636# define ARG_TLS 3
637# define ARG_CTID 4
638# endif
639
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000640int
641sys_clone(tcp)
642struct tcb *tcp;
643{
644 if (exiting(tcp)) {
Roland McGrath9677b3a2003-03-12 09:54:36 +0000645 unsigned long flags = tcp->u_arg[ARG_FLAGS];
646 tprintf("child_stack=%#lx, ", tcp->u_arg[ARG_STACK]);
647# ifdef ARG_STACKSIZE
648 if (ARG_STACKSIZE != -1)
649 tprintf("stack_size=%#lx, ",
650 tcp->u_arg[ARG_STACKSIZE]);
Roland McGrathb4968be2003-01-20 09:04:33 +0000651# endif
Roland McGrath9677b3a2003-03-12 09:54:36 +0000652 tprintf("flags=");
Roland McGrathb2dee132005-06-01 19:02:36 +0000653 printflags(clone_flags, flags &~ CSIGNAL, NULL);
Roland McGrath984154d2003-05-23 01:08:42 +0000654 if ((flags & CSIGNAL) != 0)
655 tprintf("|%s", signame(flags & CSIGNAL));
Roland McGrathb4968be2003-01-20 09:04:33 +0000656 if ((flags & (CLONE_PARENT_SETTID|CLONE_CHILD_SETTID
Roland McGrath9677b3a2003-03-12 09:54:36 +0000657 |CLONE_CHILD_CLEARTID|CLONE_SETTLS)) == 0)
Roland McGrath909875b2002-12-22 03:34:36 +0000658 return 0;
Roland McGrath6f67a982003-03-21 07:33:15 +0000659 if (flags & CLONE_PARENT_SETTID)
660 tprintf(", parent_tidptr=%#lx", tcp->u_arg[ARG_PTID]);
Roland McGrathb4968be2003-01-20 09:04:33 +0000661 if (flags & CLONE_SETTLS) {
Roland McGrath9677b3a2003-03-12 09:54:36 +0000662# ifdef I386
Roland McGrath909875b2002-12-22 03:34:36 +0000663 struct modify_ldt_ldt_s copy;
Roland McGrath9677b3a2003-03-12 09:54:36 +0000664 if (umove(tcp, tcp->u_arg[ARG_TLS], &copy) != -1) {
Roland McGrath909875b2002-12-22 03:34:36 +0000665 tprintf(", {entry_number:%d, ",
666 copy.entry_number);
667 if (!verbose(tcp))
668 tprintf("...}");
669 else
670 print_ldt_entry(&copy);
671 }
672 else
Roland McGrath9677b3a2003-03-12 09:54:36 +0000673# endif
Roland McGrath43f2c842003-03-12 09:58:14 +0000674 tprintf(", tls=%#lx", tcp->u_arg[ARG_TLS]);
Roland McGrath909875b2002-12-22 03:34:36 +0000675 }
Roland McGrath9677b3a2003-03-12 09:54:36 +0000676 if (flags & (CLONE_CHILD_SETTID|CLONE_CHILD_CLEARTID))
677 tprintf(", child_tidptr=%#lx", tcp->u_arg[ARG_CTID]);
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000678 }
679 return 0;
680}
Dmitry V. Levin95ebf5a2006-10-13 20:25:12 +0000681
682int
683sys_unshare(struct tcb *tcp)
684{
685 if (entering(tcp))
686 printflags(clone_flags, tcp->u_arg[0], "CLONE_???");
687 return 0;
688}
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000689#endif
690
Wichert Akkerman76baf7c1999-02-19 00:21:36 +0000691int
692sys_fork(tcp)
693struct tcb *tcp;
694{
695 if (exiting(tcp))
696 return RVAL_UDECIMAL;
697 return 0;
698}
699
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000700int
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000701change_syscall(struct tcb *tcp, int new)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000702{
703#if defined(LINUX)
704#if defined(I386)
705 /* Attempt to make vfork into fork, which we can follow. */
Roland McGrath5a223472002-12-15 23:58:26 +0000706 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(ORIG_EAX * 4), new) < 0)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000707 return -1;
708 return 0;
Michal Ludvig0e035502002-09-23 15:41:01 +0000709#elif defined(X86_64)
710 /* Attempt to make vfork into fork, which we can follow. */
Roland McGrath5a223472002-12-15 23:58:26 +0000711 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(ORIG_RAX * 8), new) < 0)
Michal Ludvig0e035502002-09-23 15:41:01 +0000712 return -1;
713 return 0;
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000714#elif defined(POWERPC)
Roland McGratheb285352003-01-14 09:59:00 +0000715 if (ptrace(PTRACE_POKEUSER, tcp->pid,
716 (char*)(sizeof(unsigned long)*PT_R0), new) < 0)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000717 return -1;
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000718 return 0;
Michal Ludvig10a88d02002-10-07 14:31:00 +0000719#elif defined(S390) || defined(S390X)
720 /* s390 linux after 2.4.7 has a hook in entry.S to allow this */
721 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_GPR2), new)<0)
722 return -1;
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000723 return 0;
724#elif defined(M68K)
Wichert Akkermanc7926982000-04-10 22:22:31 +0000725 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*PT_ORIG_D0), new)<0)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000726 return -1;
727 return 0;
Roland McGrath6d1a65c2004-07-12 07:44:08 +0000728#elif defined(SPARC) || defined(SPARC64)
Wichert Akkerman00a82ee2001-03-28 20:29:17 +0000729 struct regs regs;
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000730 if (ptrace(PTRACE_GETREGS, tcp->pid, (char*)&regs, 0)<0)
731 return -1;
Wichert Akkerman00a82ee2001-03-28 20:29:17 +0000732 regs.r_g1=new;
Wichert Akkerman5ae21ea2000-05-01 01:53:59 +0000733 if (ptrace(PTRACE_SETREGS, tcp->pid, (char*)&regs, 0)<0)
734 return -1;
735 return 0;
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000736#elif defined(MIPS)
Wichert Akkermanc7926982000-04-10 22:22:31 +0000737 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_V0), new)<0)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000738 return -1;
739 return 0;
740#elif defined(ALPHA)
Wichert Akkermanc7926982000-04-10 22:22:31 +0000741 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_A3), new)<0)
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000742 return -1;
743 return 0;
Dmitry V. Levin87ea1f42008-11-10 22:21:41 +0000744#elif defined(BFIN)
745 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_P0), new)<0)
746 return -1;
747 return 0;
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000748#elif defined(IA64)
Roland McGrath08267b82004-02-20 22:56:43 +0000749 if (ia32) {
750 switch (new) {
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000751 case 2:
752 break; /* x86 SYS_fork */
753 case SYS_clone:
754 new = 120;
755 break;
756 default:
Roland McGrath08267b82004-02-20 22:56:43 +0000757 fprintf(stderr, "%s: unexpected syscall %d\n",
758 __FUNCTION__, new);
759 return -1;
760 }
761 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_R1), new)<0)
762 return -1;
763 } else if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_R15), new)<0)
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000764 return -1;
765 return 0;
Wichert Akkermanc1652e22001-03-27 12:17:16 +0000766#elif defined(HPPA)
767 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_GR20), new)<0)
768 return -1;
769 return 0;
Wichert Akkermanccef6372002-05-01 16:39:22 +0000770#elif defined(SH)
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000771 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*(REG_REG0+3)), new)<0)
772 return -1;
773 return 0;
Roland McGrathf5a47772003-06-26 22:40:42 +0000774#elif defined(SH64)
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000775 /* Top half of reg encodes the no. of args n as 0x1n.
776 Assume 0 args as kernel never actually checks... */
777 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_SYSCALL),
778 0x100000 | new) < 0)
779 return -1;
780 return 0;
Roland McGrathf691bd22006-04-25 07:34:41 +0000781#elif defined(ARM)
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000782 /* Some kernels support this, some (pre-2.6.16 or so) don't. */
Roland McGrathf691bd22006-04-25 07:34:41 +0000783# ifndef PTRACE_SET_SYSCALL
784# define PTRACE_SET_SYSCALL 23
785# endif
786
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000787 if (ptrace (PTRACE_SET_SYSCALL, tcp->pid, 0, new) != 0)
Roland McGrathf691bd22006-04-25 07:34:41 +0000788 return -1;
789
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000790 return 0;
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000791#else
792#warning Do not know how to handle change_syscall for this architecture
793#endif /* architecture */
794#endif /* LINUX */
795 return -1;
796}
797
Roland McGratha4d48532005-06-08 20:45:28 +0000798#if 0
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000799int
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000800setarg(tcp, argnum)
801 struct tcb *tcp;
802 int argnum;
803{
804#if defined (IA64)
805 {
806 unsigned long *bsp, *ap;
807
Denys Vlasenko932fc7d2008-12-16 18:18:40 +0000808 if (upeek(tcp, PT_AR_BSP, (long *) &bsp) , 0)
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000809 return -1;
810
811 ap = ia64_rse_skip_regs(bsp, argnum);
812 errno = 0;
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000813 ptrace(PTRACE_POKEDATA, tcp->pid, (char *) ap, tcp->u_arg[argnum]);
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000814 if (errno)
815 return -1;
816
817 }
Wichert Akkerman12f75d12000-02-14 16:23:40 +0000818#elif defined(I386)
819 {
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000820 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*argnum), tcp->u_arg[argnum]);
Wichert Akkerman12f75d12000-02-14 16:23:40 +0000821 if (errno)
822 return -1;
823 }
Michal Ludvig0e035502002-09-23 15:41:01 +0000824#elif defined(X86_64)
825 {
826 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(8*(long)argnum), tcp->u_arg[argnum]);
827 if (errno)
828 return -1;
829 }
Roland McGrath3bb9c3d2002-12-16 20:40:48 +0000830#elif defined(POWERPC)
831#ifndef PT_ORIG_R3
832#define PT_ORIG_R3 34
833#endif
834 {
835 ptrace(PTRACE_POKEUSER, tcp->pid,
Roland McGratheb285352003-01-14 09:59:00 +0000836 (char*)((argnum==0 ? PT_ORIG_R3 : argnum+PT_R3)*sizeof(unsigned long)),
Roland McGrath3bb9c3d2002-12-16 20:40:48 +0000837 tcp->u_arg[argnum]);
838 if (errno)
839 return -1;
840 }
Ralf Baechlee3816102000-08-01 00:06:06 +0000841#elif defined(MIPS)
842 {
843 errno = 0;
844 if (argnum < 4)
845 ptrace(PTRACE_POKEUSER, tcp->pid,
846 (char*)(REG_A0 + argnum), tcp->u_arg[argnum]);
847 else {
848 unsigned long *sp;
849
Denys Vlasenko932fc7d2008-12-16 18:18:40 +0000850 if (upeek(tcp, REG_SP, (long *) &sp) , 0)
Ralf Baechlee3816102000-08-01 00:06:06 +0000851 return -1;
852
853 ptrace(PTRACE_POKEDATA, tcp->pid,
854 (char*)(sp + argnum - 4), tcp->u_arg[argnum]);
855 }
856 if (errno)
857 return -1;
858 }
Michal Ludvig10a88d02002-10-07 14:31:00 +0000859#elif defined(S390) || defined(S390X)
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000860 {
Michal Ludvig10a88d02002-10-07 14:31:00 +0000861 if(argnum <= 5)
862 ptrace(PTRACE_POKEUSER, tcp->pid,
Roland McGrath5a223472002-12-15 23:58:26 +0000863 (char *) (argnum==0 ? PT_ORIGGPR2 :
864 PT_GPR2 + argnum*sizeof(long)),
Michal Ludvig10a88d02002-10-07 14:31:00 +0000865 tcp->u_arg[argnum]);
866 else
867 return -E2BIG;
868 if (errno)
869 return -1;
Denys Vlasenkoadedb512008-12-30 18:47:55 +0000870 }
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000871#else
Wichert Akkermanfaf72222000-02-19 23:59:03 +0000872# warning Sorry, setargs not implemented for this architecture.
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000873#endif
874 return 0;
875}
Roland McGratha4d48532005-06-08 20:45:28 +0000876#endif
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000877
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000878#if defined SYS_clone || defined SYS_clone2
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000879int
880internal_clone(tcp)
881struct tcb *tcp;
882{
Ulrich Drepper90512f01999-12-24 07:22:25 +0000883 struct tcb *tcpchild;
884 int pid;
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000885 if (entering(tcp)) {
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +0000886 if (!followfork)
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000887 return 0;
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000888 fork_tcb(tcp);
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000889 if (setbpt(tcp) < 0)
890 return 0;
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000891 } else {
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000892 int bpt = tcp->flags & TCB_BPTSET;
893
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000894 if (!(tcp->flags & TCB_FOLLOWFORK))
895 return 0;
896
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000897 if (syserror(tcp)) {
898 if (bpt)
899 clearbpt(tcp);
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000900 return 0;
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000901 }
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000902
903 pid = tcp->u_rval;
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000904
905#ifdef CLONE_PTRACE /* See new setbpt code. */
906 tcpchild = pid2tcb(pid);
907 if (tcpchild != NULL) {
908 /* The child already reported its startup trap
909 before the parent reported its syscall return. */
910 if ((tcpchild->flags
911 & (TCB_STARTUP|TCB_ATTACHED|TCB_SUSPENDED))
912 != (TCB_STARTUP|TCB_ATTACHED|TCB_SUSPENDED))
913 fprintf(stderr, "\
914[preattached child %d of %d in weird state!]\n",
915 pid, tcp->pid);
916 }
917 else
918#endif
Denys Vlasenko418d66a2009-01-17 01:52:54 +0000919 fork_tcb(tcp);
920 tcpchild = alloctcb(pid);
Wichert Akkerman7a0b6491999-12-23 15:08:17 +0000921
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000922#ifndef CLONE_PTRACE
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000923 /* Attach to the new child */
924 if (ptrace(PTRACE_ATTACH, pid, (char *) 1, 0) < 0) {
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000925 if (bpt)
926 clearbpt(tcp);
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000927 perror("PTRACE_ATTACH");
928 fprintf(stderr, "Too late?\n");
929 droptcb(tcpchild);
930 return 0;
931 }
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000932#endif
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000933
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000934 if (bpt)
935 clearbpt(tcp);
936
Ulrich Drepper90512f01999-12-24 07:22:25 +0000937 tcpchild->flags |= TCB_ATTACHED;
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000938 /* Child has BPT too, must be removed on first occasion. */
Wichert Akkerman9b0c31d2000-09-03 21:56:29 +0000939 if (bpt) {
940 tcpchild->flags |= TCB_BPTSET;
941 tcpchild->baddr = tcp->baddr;
942 memcpy(tcpchild->inst, tcp->inst,
943 sizeof tcpchild->inst);
944 }
Wichert Akkerman7b3346b2001-10-09 23:47:38 +0000945 tcpchild->parent = tcp;
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000946 tcp->nchildren++;
947 if (tcpchild->flags & TCB_SUSPENDED) {
948 /* The child was born suspended, due to our having
949 forced CLONE_PTRACE. */
950 if (bpt)
951 clearbpt(tcpchild);
952
953 tcpchild->flags &= ~(TCB_SUSPENDED|TCB_STARTUP);
Denys Vlasenkof9a7e632009-01-17 00:21:31 +0000954 /* TCB_SUSPENDED tasks are not collected by waitpid
955 * loop, and left stopped. Restart it:
956 */
Denys Vlasenko732d1bf2008-12-17 19:21:59 +0000957 if (ptrace_restart(PTRACE_SYSCALL, tcpchild, 0) < 0)
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000958 return -1;
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000959
960 if (!qflag)
961 fprintf(stderr, "\
962Process %u resumed (parent %d ready)\n",
963 pid, tcp->pid);
964 }
965 else {
Roland McGrathe85bbfe2003-01-09 06:53:31 +0000966 if (!qflag)
967 fprintf(stderr, "Process %d attached\n", pid);
968 }
969
970#ifdef TCB_CLONE_THREAD
Roland McGrath984154d2003-05-23 01:08:42 +0000971 {
972 /*
973 * Save the flags used in this call,
974 * in case we point TCP to our parent below.
975 */
976 int call_flags = tcp->u_arg[ARG_FLAGS];
977 if ((tcp->flags & TCB_CLONE_THREAD) &&
978 tcp->parent != NULL) {
979 /* The parent in this clone is itself a
980 thread belonging to another process.
981 There is no meaning to the parentage
982 relationship of the new child with the
983 thread, only with the process. We
984 associate the new thread with our
985 parent. Since this is done for every
986 new thread, there will never be a
987 TCB_CLONE_THREAD process that has
988 children. */
989 --tcp->nchildren;
990 tcp = tcp->parent;
991 tcpchild->parent = tcp;
992 ++tcp->nchildren;
993 }
994 if (call_flags & CLONE_THREAD) {
995 tcpchild->flags |= TCB_CLONE_THREAD;
996 ++tcp->nclone_threads;
997 }
998 if (call_flags & CLONE_DETACHED) {
999 tcpchild->flags |= TCB_CLONE_DETACHED;
1000 ++tcp->nclone_detached;
1001 }
Roland McGrathe85bbfe2003-01-09 06:53:31 +00001002 }
1003#endif
1004
1005 }
Wichert Akkerman7a0b6491999-12-23 15:08:17 +00001006 return 0;
1007}
1008#endif
1009
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001010int
1011internal_fork(tcp)
1012struct tcb *tcp;
1013{
Roland McGrathe85bbfe2003-01-09 06:53:31 +00001014#ifdef LINUX
1015 /* We do special magic with clone for any clone or fork. */
1016 return internal_clone(tcp);
1017#else
1018
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001019 struct tcb *tcpchild;
1020 int pid;
Nate Sammonsccd8f211999-03-29 22:57:54 +00001021 int dont_follow = 0;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001022
1023#ifdef SYS_vfork
Roland McGratha4f9f2d2005-06-07 23:21:20 +00001024 if (known_scno(tcp) == SYS_vfork) {
Nate Sammonsccd8f211999-03-29 22:57:54 +00001025 /* Attempt to make vfork into fork, which we can follow. */
Roland McGrath41c48222008-07-18 00:25:10 +00001026 if (change_syscall(tcp, SYS_fork) < 0)
Nate Sammonsccd8f211999-03-29 22:57:54 +00001027 dont_follow = 1;
Nate Sammonsccd8f211999-03-29 22:57:54 +00001028 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001029#endif
1030 if (entering(tcp)) {
Nate Sammonsccd8f211999-03-29 22:57:54 +00001031 if (!followfork || dont_follow)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001032 return 0;
Denys Vlasenko418d66a2009-01-17 01:52:54 +00001033 fork_tcb(tcp);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001034 if (setbpt(tcp) < 0)
1035 return 0;
Wichert Akkerman7a0b6491999-12-23 15:08:17 +00001036 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001037 else {
1038 int bpt = tcp->flags & TCB_BPTSET;
1039
1040 if (!(tcp->flags & TCB_FOLLOWFORK))
1041 return 0;
1042 if (bpt)
1043 clearbpt(tcp);
1044
1045 if (syserror(tcp))
1046 return 0;
1047
1048 pid = tcp->u_rval;
Denys Vlasenko418d66a2009-01-17 01:52:54 +00001049 fork_tcb(tcp);
1050 tcpchild = alloctcb(pid);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001051#ifdef LINUX
Wichert Akkermanc1652e22001-03-27 12:17:16 +00001052#ifdef HPPA
1053 /* The child must have run before it can be attached. */
1054 /* This must be a bug in the parisc kernel, but I havn't
1055 * identified it yet. Seems to be an issue associated
1056 * with attaching to a process (which sends it a signal)
1057 * before that process has ever been scheduled. When
1058 * debugging, I started seeing crashes in
1059 * arch/parisc/kernel/signal.c:do_signal(), apparently
1060 * caused by r8 getting corrupt over the dequeue_signal()
1061 * call. Didn't make much sense though...
1062 */
1063 {
1064 struct timeval tv;
1065 tv.tv_sec = 0;
1066 tv.tv_usec = 10000;
1067 select(0, NULL, NULL, NULL, &tv);
1068 }
1069#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001070 if (ptrace(PTRACE_ATTACH, pid, (char *) 1, 0) < 0) {
1071 perror("PTRACE_ATTACH");
1072 fprintf(stderr, "Too late?\n");
1073 droptcb(tcpchild);
1074 return 0;
1075 }
1076#endif /* LINUX */
1077#ifdef SUNOS4
1078#ifdef oldway
1079 /* The child must have run before it can be attached. */
1080 {
1081 struct timeval tv;
1082 tv.tv_sec = 0;
1083 tv.tv_usec = 10000;
1084 select(0, NULL, NULL, NULL, &tv);
1085 }
1086 if (ptrace(PTRACE_ATTACH, pid, (char *)1, 0) < 0) {
1087 perror("PTRACE_ATTACH");
1088 fprintf(stderr, "Too late?\n");
1089 droptcb(tcpchild);
1090 return 0;
1091 }
1092#else /* !oldway */
1093 /* Try to catch the new process as soon as possible. */
1094 {
1095 int i;
1096 for (i = 0; i < 1024; i++)
1097 if (ptrace(PTRACE_ATTACH, pid, (char *) 1, 0) >= 0)
1098 break;
1099 if (i == 1024) {
1100 perror("PTRACE_ATTACH");
1101 fprintf(stderr, "Too late?\n");
1102 droptcb(tcpchild);
1103 return 0;
1104 }
1105 }
1106#endif /* !oldway */
1107#endif /* SUNOS4 */
1108 tcpchild->flags |= TCB_ATTACHED;
1109 /* Child has BPT too, must be removed on first occasion */
1110 if (bpt) {
1111 tcpchild->flags |= TCB_BPTSET;
1112 tcpchild->baddr = tcp->baddr;
1113 memcpy(tcpchild->inst, tcp->inst,
1114 sizeof tcpchild->inst);
1115 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001116 tcpchild->parent = tcp;
1117 tcp->nchildren++;
1118 if (!qflag)
1119 fprintf(stderr, "Process %d attached\n", pid);
1120 }
1121 return 0;
Roland McGrathe85bbfe2003-01-09 06:53:31 +00001122#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001123}
1124
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00001125#endif /* !USE_PROCFS */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001126
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00001127#if defined(SUNOS4) || defined(LINUX) || defined(FREEBSD)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001128
1129int
1130sys_vfork(tcp)
1131struct tcb *tcp;
1132{
1133 if (exiting(tcp))
1134 return RVAL_UDECIMAL;
1135 return 0;
1136}
1137
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00001138#endif /* SUNOS4 || LINUX || FREEBSD */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001139
1140#ifndef LINUX
1141
1142static char idstr[16];
1143
1144int
1145sys_getpid(tcp)
1146struct tcb *tcp;
1147{
1148 if (exiting(tcp)) {
1149 sprintf(idstr, "ppid %lu", getrval2(tcp));
1150 tcp->auxstr = idstr;
1151 return RVAL_STR;
1152 }
1153 return 0;
1154}
1155
1156int
1157sys_getuid(tcp)
1158struct tcb *tcp;
1159{
1160 if (exiting(tcp)) {
1161 sprintf(idstr, "euid %lu", getrval2(tcp));
1162 tcp->auxstr = idstr;
1163 return RVAL_STR;
1164 }
1165 return 0;
1166}
1167
1168int
1169sys_getgid(tcp)
1170struct tcb *tcp;
1171{
1172 if (exiting(tcp)) {
1173 sprintf(idstr, "egid %lu", getrval2(tcp));
1174 tcp->auxstr = idstr;
1175 return RVAL_STR;
1176 }
1177 return 0;
1178}
1179
1180#endif /* !LINUX */
1181
1182#ifdef LINUX
1183
1184int
1185sys_setuid(tcp)
1186struct tcb *tcp;
1187{
1188 if (entering(tcp)) {
1189 tprintf("%u", (uid_t) tcp->u_arg[0]);
1190 }
1191 return 0;
1192}
1193
1194int
1195sys_setgid(tcp)
1196struct tcb *tcp;
1197{
1198 if (entering(tcp)) {
1199 tprintf("%u", (gid_t) tcp->u_arg[0]);
1200 }
1201 return 0;
1202}
1203
1204int
1205sys_getresuid(tcp)
1206 struct tcb *tcp;
1207{
1208 if (exiting(tcp)) {
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001209 __kernel_uid_t uid;
1210 if (syserror(tcp))
1211 tprintf("%#lx, %#lx, %#lx", tcp->u_arg[0],
1212 tcp->u_arg[1], tcp->u_arg[2]);
1213 else {
1214 if (umove(tcp, tcp->u_arg[0], &uid) < 0)
1215 tprintf("%#lx, ", tcp->u_arg[0]);
1216 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001217 tprintf("[%lu], ", (unsigned long) uid);
Roland McGrath9bd6b422003-02-24 07:13:51 +00001218 if (umove(tcp, tcp->u_arg[1], &uid) < 0)
1219 tprintf("%#lx, ", tcp->u_arg[1]);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001220 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001221 tprintf("[%lu], ", (unsigned long) uid);
Roland McGrath9bd6b422003-02-24 07:13:51 +00001222 if (umove(tcp, tcp->u_arg[2], &uid) < 0)
1223 tprintf("%#lx", tcp->u_arg[2]);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001224 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001225 tprintf("[%lu]", (unsigned long) uid);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001226 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001227 }
1228 return 0;
1229}
1230
1231int
1232sys_getresgid(tcp)
1233struct tcb *tcp;
1234{
1235 if (exiting(tcp)) {
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001236 __kernel_gid_t gid;
1237 if (syserror(tcp))
1238 tprintf("%#lx, %#lx, %#lx", tcp->u_arg[0],
1239 tcp->u_arg[1], tcp->u_arg[2]);
1240 else {
1241 if (umove(tcp, tcp->u_arg[0], &gid) < 0)
1242 tprintf("%#lx, ", tcp->u_arg[0]);
1243 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001244 tprintf("[%lu], ", (unsigned long) gid);
Roland McGrathd2450922003-02-24 10:18:07 +00001245 if (umove(tcp, tcp->u_arg[1], &gid) < 0)
1246 tprintf("%#lx, ", tcp->u_arg[1]);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001247 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001248 tprintf("[%lu], ", (unsigned long) gid);
Roland McGrathd2450922003-02-24 10:18:07 +00001249 if (umove(tcp, tcp->u_arg[2], &gid) < 0)
1250 tprintf("%#lx", tcp->u_arg[2]);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001251 else
Roland McGrath83bd47a2003-11-13 22:32:26 +00001252 tprintf("[%lu]", (unsigned long) gid);
Wichert Akkerman2e2553a1999-05-09 00:29:58 +00001253 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001254 }
1255 return 0;
1256}
1257
1258#endif /* LINUX */
1259
1260int
1261sys_setreuid(tcp)
1262struct tcb *tcp;
1263{
1264 if (entering(tcp)) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001265 printuid("", tcp->u_arg[0]);
1266 printuid(", ", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001267 }
1268 return 0;
1269}
1270
1271int
1272sys_setregid(tcp)
1273struct tcb *tcp;
1274{
1275 if (entering(tcp)) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001276 printuid("", tcp->u_arg[0]);
1277 printuid(", ", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001278 }
1279 return 0;
1280}
1281
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00001282#if defined(LINUX) || defined(FREEBSD)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001283int
1284sys_setresuid(tcp)
1285 struct tcb *tcp;
1286{
1287 if (entering(tcp)) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001288 printuid("", tcp->u_arg[0]);
1289 printuid(", ", tcp->u_arg[1]);
1290 printuid(", ", tcp->u_arg[2]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001291 }
1292 return 0;
1293}
1294int
1295sys_setresgid(tcp)
1296 struct tcb *tcp;
1297{
1298 if (entering(tcp)) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001299 printuid("", tcp->u_arg[0]);
1300 printuid(", ", tcp->u_arg[1]);
1301 printuid(", ", tcp->u_arg[2]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001302 }
1303 return 0;
1304}
1305
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00001306#endif /* LINUX || FREEBSD */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001307
1308int
1309sys_setgroups(tcp)
1310struct tcb *tcp;
1311{
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001312 if (entering(tcp)) {
Roland McGrathaa524c82005-06-01 19:22:06 +00001313 unsigned long len, size, start, cur, end, abbrev_end;
1314 GETGROUPS_T gid;
1315 int failed = 0;
1316
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001317 len = tcp->u_arg[0];
Roland McGrathaa524c82005-06-01 19:22:06 +00001318 tprintf("%lu, ", len);
1319 if (len == 0) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001320 tprintf("[]");
1321 return 0;
1322 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001323 start = tcp->u_arg[1];
1324 if (start == 0) {
1325 tprintf("NULL");
1326 return 0;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001327 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001328 size = len * sizeof(gid);
1329 end = start + size;
1330 if (!verbose(tcp) || size / sizeof(gid) != len || end < start) {
1331 tprintf("%#lx", start);
1332 return 0;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001333 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001334 if (abbrev(tcp)) {
1335 abbrev_end = start + max_strlen * sizeof(gid);
1336 if (abbrev_end < start)
1337 abbrev_end = end;
1338 } else {
1339 abbrev_end = end;
1340 }
1341 tprintf("[");
1342 for (cur = start; cur < end; cur += sizeof(gid)) {
1343 if (cur > start)
1344 tprintf(", ");
1345 if (cur >= abbrev_end) {
1346 tprintf("...");
1347 break;
1348 }
1349 if (umoven(tcp, cur, sizeof(gid), (char *) &gid) < 0) {
1350 tprintf("?");
1351 failed = 1;
1352 break;
1353 }
1354 tprintf("%lu", (unsigned long) gid);
1355 }
1356 tprintf("]");
1357 if (failed)
1358 tprintf(" %#lx", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001359 }
1360 return 0;
1361}
1362
1363int
1364sys_getgroups(tcp)
1365struct tcb *tcp;
1366{
Roland McGrathaa524c82005-06-01 19:22:06 +00001367 unsigned long len;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001368
1369 if (entering(tcp)) {
1370 len = tcp->u_arg[0];
Roland McGrathaa524c82005-06-01 19:22:06 +00001371 tprintf("%lu, ", len);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001372 } else {
Roland McGrathaa524c82005-06-01 19:22:06 +00001373 unsigned long size, start, cur, end, abbrev_end;
1374 GETGROUPS_T gid;
1375 int failed = 0;
1376
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001377 len = tcp->u_rval;
Roland McGrathaa524c82005-06-01 19:22:06 +00001378 if (len == 0) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001379 tprintf("[]");
1380 return 0;
1381 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001382 start = tcp->u_arg[1];
1383 if (start == 0) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001384 tprintf("NULL");
Roland McGrathaa524c82005-06-01 19:22:06 +00001385 return 0;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001386 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001387 if (tcp->u_arg[0] == 0) {
1388 tprintf("%#lx", start);
1389 return 0;
1390 }
1391 size = len * sizeof(gid);
1392 end = start + size;
1393 if (!verbose(tcp) || tcp->u_arg[0] == 0 ||
1394 size / sizeof(gid) != len || end < start) {
1395 tprintf("%#lx", start);
1396 return 0;
1397 }
1398 if (abbrev(tcp)) {
1399 abbrev_end = start + max_strlen * sizeof(gid);
1400 if (abbrev_end < start)
1401 abbrev_end = end;
1402 } else {
1403 abbrev_end = end;
1404 }
1405 tprintf("[");
1406 for (cur = start; cur < end; cur += sizeof(gid)) {
1407 if (cur > start)
1408 tprintf(", ");
1409 if (cur >= abbrev_end) {
1410 tprintf("...");
1411 break;
1412 }
1413 if (umoven(tcp, cur, sizeof(gid), (char *) &gid) < 0) {
1414 tprintf("?");
1415 failed = 1;
1416 break;
1417 }
1418 tprintf("%lu", (unsigned long) gid);
1419 }
1420 tprintf("]");
1421 if (failed)
1422 tprintf(" %#lx", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001423 }
1424 return 0;
1425}
1426
Roland McGrath83bd47a2003-11-13 22:32:26 +00001427#ifdef LINUX
1428int
1429sys_setgroups32(tcp)
1430struct tcb *tcp;
1431{
Roland McGrath83bd47a2003-11-13 22:32:26 +00001432 if (entering(tcp)) {
Roland McGrathaa524c82005-06-01 19:22:06 +00001433 unsigned long len, size, start, cur, end, abbrev_end;
1434 GETGROUPS32_T gid;
1435 int failed = 0;
1436
Roland McGrath83bd47a2003-11-13 22:32:26 +00001437 len = tcp->u_arg[0];
Roland McGrathaa524c82005-06-01 19:22:06 +00001438 tprintf("%lu, ", len);
1439 if (len == 0) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001440 tprintf("[]");
1441 return 0;
1442 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001443 start = tcp->u_arg[1];
1444 if (start == 0) {
1445 tprintf("NULL");
1446 return 0;
Roland McGrath83bd47a2003-11-13 22:32:26 +00001447 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001448 size = len * sizeof(gid);
1449 end = start + size;
1450 if (!verbose(tcp) || size / sizeof(gid) != len || end < start) {
1451 tprintf("%#lx", start);
1452 return 0;
Roland McGrath83bd47a2003-11-13 22:32:26 +00001453 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001454 if (abbrev(tcp)) {
1455 abbrev_end = start + max_strlen * sizeof(gid);
1456 if (abbrev_end < start)
1457 abbrev_end = end;
1458 } else {
1459 abbrev_end = end;
1460 }
1461 tprintf("[");
1462 for (cur = start; cur < end; cur += sizeof(gid)) {
1463 if (cur > start)
1464 tprintf(", ");
1465 if (cur >= abbrev_end) {
1466 tprintf("...");
1467 break;
1468 }
1469 if (umoven(tcp, cur, sizeof(gid), (char *) &gid) < 0) {
1470 tprintf("?");
1471 failed = 1;
1472 break;
1473 }
1474 tprintf("%lu", (unsigned long) gid);
1475 }
1476 tprintf("]");
1477 if (failed)
1478 tprintf(" %#lx", tcp->u_arg[1]);
Roland McGrath83bd47a2003-11-13 22:32:26 +00001479 }
1480 return 0;
1481}
1482
1483int
1484sys_getgroups32(tcp)
1485struct tcb *tcp;
1486{
Roland McGrathaa524c82005-06-01 19:22:06 +00001487 unsigned long len;
Roland McGrath83bd47a2003-11-13 22:32:26 +00001488
1489 if (entering(tcp)) {
1490 len = tcp->u_arg[0];
Roland McGrathaa524c82005-06-01 19:22:06 +00001491 tprintf("%lu, ", len);
Roland McGrath83bd47a2003-11-13 22:32:26 +00001492 } else {
Roland McGrathaa524c82005-06-01 19:22:06 +00001493 unsigned long size, start, cur, end, abbrev_end;
1494 GETGROUPS32_T gid;
1495 int failed = 0;
1496
Roland McGrath83bd47a2003-11-13 22:32:26 +00001497 len = tcp->u_rval;
Roland McGrathaa524c82005-06-01 19:22:06 +00001498 if (len == 0) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001499 tprintf("[]");
1500 return 0;
1501 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001502 start = tcp->u_arg[1];
1503 if (start == 0) {
Roland McGrath83bd47a2003-11-13 22:32:26 +00001504 tprintf("NULL");
Roland McGrathaa524c82005-06-01 19:22:06 +00001505 return 0;
Roland McGrath83bd47a2003-11-13 22:32:26 +00001506 }
Roland McGrathaa524c82005-06-01 19:22:06 +00001507 size = len * sizeof(gid);
1508 end = start + size;
1509 if (!verbose(tcp) || tcp->u_arg[0] == 0 ||
1510 size / sizeof(gid) != len || end < start) {
1511 tprintf("%#lx", start);
1512 return 0;
1513 }
1514 if (abbrev(tcp)) {
1515 abbrev_end = start + max_strlen * sizeof(gid);
1516 if (abbrev_end < start)
1517 abbrev_end = end;
1518 } else {
1519 abbrev_end = end;
1520 }
1521 tprintf("[");
1522 for (cur = start; cur < end; cur += sizeof(gid)) {
1523 if (cur > start)
1524 tprintf(", ");
1525 if (cur >= abbrev_end) {
1526 tprintf("...");
1527 break;
1528 }
1529 if (umoven(tcp, cur, sizeof(gid), (char *) &gid) < 0) {
1530 tprintf("?");
1531 failed = 1;
1532 break;
1533 }
1534 tprintf("%lu", (unsigned long) gid);
1535 }
1536 tprintf("]");
1537 if (failed)
1538 tprintf(" %#lx", tcp->u_arg[1]);
Roland McGrath83bd47a2003-11-13 22:32:26 +00001539 }
1540 return 0;
1541}
1542#endif /* LINUX */
1543
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +00001544#if defined(ALPHA) || defined(SUNOS4) || defined(SVR4)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001545int
1546sys_setpgrp(tcp)
1547struct tcb *tcp;
1548{
1549 if (entering(tcp)) {
1550#ifndef SVR4
1551 tprintf("%lu, %lu", tcp->u_arg[0], tcp->u_arg[1]);
1552#endif /* !SVR4 */
1553 }
1554 return 0;
1555}
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +00001556#endif /* ALPHA || SUNOS4 || SVR4 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001557
1558int
1559sys_getpgrp(tcp)
1560struct tcb *tcp;
1561{
1562 if (entering(tcp)) {
1563#ifndef SVR4
1564 tprintf("%lu", tcp->u_arg[0]);
1565#endif /* !SVR4 */
1566 }
1567 return 0;
1568}
1569
1570int
1571sys_getsid(tcp)
1572struct tcb *tcp;
1573{
1574 if (entering(tcp)) {
1575 tprintf("%lu", tcp->u_arg[0]);
1576 }
1577 return 0;
1578}
1579
1580int
1581sys_setsid(tcp)
1582struct tcb *tcp;
1583{
1584 return 0;
1585}
1586
1587int
1588sys_getpgid(tcp)
1589struct tcb *tcp;
1590{
1591 if (entering(tcp)) {
1592 tprintf("%lu", tcp->u_arg[0]);
1593 }
1594 return 0;
1595}
1596
1597int
1598sys_setpgid(tcp)
1599struct tcb *tcp;
1600{
1601 if (entering(tcp)) {
1602 tprintf("%lu, %lu", tcp->u_arg[0], tcp->u_arg[1]);
1603 }
1604 return 0;
1605}
1606
John Hughesc61eb3d2002-05-17 11:37:50 +00001607#if UNIXWARE >= 2
1608
1609#include <sys/privilege.h>
1610
1611
Roland McGrathd9f816f2004-09-04 03:39:20 +00001612static const struct xlat procpriv_cmds [] = {
John Hughesc61eb3d2002-05-17 11:37:50 +00001613 { SETPRV, "SETPRV" },
1614 { CLRPRV, "CLRPRV" },
1615 { PUTPRV, "PUTPRV" },
1616 { GETPRV, "GETPRV" },
1617 { CNTPRV, "CNTPRV" },
1618 { 0, NULL },
1619};
1620
1621
Roland McGrathd9f816f2004-09-04 03:39:20 +00001622static const struct xlat procpriv_priv [] = {
John Hughesc61eb3d2002-05-17 11:37:50 +00001623 { P_OWNER, "P_OWNER" },
1624 { P_AUDIT, "P_AUDIT" },
1625 { P_COMPAT, "P_COMPAT" },
1626 { P_DACREAD, "P_DACREAD" },
1627 { P_DACWRITE, "P_DACWRITE" },
1628 { P_DEV, "P_DEV" },
1629 { P_FILESYS, "P_FILESYS" },
1630 { P_MACREAD, "P_MACREAD" },
1631 { P_MACWRITE, "P_MACWRITE" },
1632 { P_MOUNT, "P_MOUNT" },
1633 { P_MULTIDIR, "P_MULTIDIR" },
1634 { P_SETPLEVEL, "P_SETPLEVEL" },
1635 { P_SETSPRIV, "P_SETSPRIV" },
1636 { P_SETUID, "P_SETUID" },
1637 { P_SYSOPS, "P_SYSOPS" },
1638 { P_SETUPRIV, "P_SETUPRIV" },
1639 { P_DRIVER, "P_DRIVER" },
1640 { P_RTIME, "P_RTIME" },
1641 { P_MACUPGRADE, "P_MACUPGRADE" },
1642 { P_FSYSRANGE, "P_FSYSRANGE" },
1643 { P_SETFLEVEL, "P_SETFLEVEL" },
1644 { P_AUDITWR, "P_AUDITWR" },
1645 { P_TSHAR, "P_TSHAR" },
1646 { P_PLOCK, "P_PLOCK" },
1647 { P_CORE, "P_CORE" },
1648 { P_LOADMOD, "P_LOADMOD" },
1649 { P_BIND, "P_BIND" },
1650 { P_ALLPRIVS, "P_ALLPRIVS" },
1651 { 0, NULL },
1652};
1653
1654
Roland McGrathd9f816f2004-09-04 03:39:20 +00001655static const struct xlat procpriv_type [] = {
John Hughesc61eb3d2002-05-17 11:37:50 +00001656 { PS_FIX, "PS_FIX" },
1657 { PS_INH, "PS_INH" },
1658 { PS_MAX, "PS_MAX" },
1659 { PS_WKG, "PS_WKG" },
1660 { 0, NULL },
1661};
1662
1663
1664static void
Dmitry V. Levinab9008b2007-01-11 22:05:04 +00001665printpriv(struct tcb *tcp, long addr, int len, const struct xlat *opt)
John Hughesc61eb3d2002-05-17 11:37:50 +00001666{
1667 priv_t buf [128];
1668 int max = verbose (tcp) ? sizeof buf / sizeof buf [0] : 10;
1669 int dots = len > max;
1670 int i;
Roland McGrath5a223472002-12-15 23:58:26 +00001671
John Hughesc61eb3d2002-05-17 11:37:50 +00001672 if (len > max) len = max;
Roland McGrath5a223472002-12-15 23:58:26 +00001673
John Hughesc61eb3d2002-05-17 11:37:50 +00001674 if (len <= 0 ||
1675 umoven (tcp, addr, len * sizeof buf[0], (char *) buf) < 0)
1676 {
1677 tprintf ("%#lx", addr);
1678 return;
1679 }
1680
1681 tprintf ("[");
1682
1683 for (i = 0; i < len; ++i) {
Dmitry V. Levinab9008b2007-01-11 22:05:04 +00001684 const char *t, *p;
John Hughesc61eb3d2002-05-17 11:37:50 +00001685
1686 if (i) tprintf (", ");
1687
1688 if ((t = xlookup (procpriv_type, buf [i] & PS_TYPE)) &&
1689 (p = xlookup (procpriv_priv, buf [i] & ~PS_TYPE)))
1690 {
1691 tprintf ("%s|%s", t, p);
1692 }
1693 else {
1694 tprintf ("%#lx", buf [i]);
1695 }
1696 }
1697
1698 if (dots) tprintf (" ...");
1699
1700 tprintf ("]");
1701}
1702
1703
1704int
1705sys_procpriv(tcp)
1706struct tcb *tcp;
1707{
1708 if (entering(tcp)) {
1709 printxval(procpriv_cmds, tcp->u_arg[0], "???PRV");
1710 switch (tcp->u_arg[0]) {
1711 case CNTPRV:
1712 tprintf(", %#lx, %ld", tcp->u_arg[1], tcp->u_arg[2]);
1713 break;
1714
1715 case GETPRV:
1716 break;
1717
1718 default:
1719 tprintf (", ");
1720 printpriv (tcp, tcp->u_arg[1], tcp->u_arg[2]);
1721 tprintf (", %ld", tcp->u_arg[2]);
1722 }
1723 }
1724 else if (tcp->u_arg[0] == GETPRV) {
1725 if (syserror (tcp)) {
1726 tprintf(", %#lx, %ld", tcp->u_arg[1], tcp->u_arg[2]);
1727 }
1728 else {
1729 tprintf (", ");
1730 printpriv (tcp, tcp->u_arg[1], tcp->u_rval);
1731 tprintf (", %ld", tcp->u_arg[2]);
1732 }
1733 }
Roland McGrath5a223472002-12-15 23:58:26 +00001734
John Hughesc61eb3d2002-05-17 11:37:50 +00001735 return 0;
1736}
1737
1738#endif
1739
1740
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001741static void
1742printargv(tcp, addr)
1743struct tcb *tcp;
1744long addr;
1745{
Roland McGrath85a3bc42007-08-02 02:13:05 +00001746 union {
1747 int p32;
1748 long p64;
1749 char data[sizeof(long)];
1750 } cp;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001751 char *sep;
Roland McGrath85a3bc42007-08-02 02:13:05 +00001752 int n = 0;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001753
Roland McGrath85a3bc42007-08-02 02:13:05 +00001754 cp.p64 = 1;
1755 for (sep = ""; !abbrev(tcp) || n < max_strlen / 2; sep = ", ", ++n) {
1756 if (umoven(tcp, addr, personality_wordsize[current_personality],
1757 cp.data) < 0) {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001758 tprintf("%#lx", addr);
1759 return;
1760 }
Roland McGrath85a3bc42007-08-02 02:13:05 +00001761 if (personality_wordsize[current_personality] == 4)
1762 cp.p64 = cp.p32;
1763 if (cp.p64 == 0)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001764 break;
1765 tprintf(sep);
Roland McGrath85a3bc42007-08-02 02:13:05 +00001766 printstr(tcp, cp.p64, -1);
1767 addr += personality_wordsize[current_personality];
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001768 }
Roland McGrath85a3bc42007-08-02 02:13:05 +00001769 if (cp.p64)
1770 tprintf("%s...", sep);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001771}
1772
1773static void
1774printargc(fmt, tcp, addr)
1775char *fmt;
1776struct tcb *tcp;
1777long addr;
1778{
1779 int count;
1780 char *cp;
1781
1782 for (count = 0; umove(tcp, addr, &cp) >= 0 && cp != NULL; count++) {
1783 addr += sizeof(char *);
1784 }
1785 tprintf(fmt, count, count == 1 ? "" : "s");
1786}
1787
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +00001788#if defined(SPARC) || defined(SPARC64) || defined(SUNOS4)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001789int
1790sys_execv(tcp)
1791struct tcb *tcp;
1792{
1793 if (entering(tcp)) {
1794 printpath(tcp, tcp->u_arg[0]);
1795 if (!verbose(tcp))
1796 tprintf(", %#lx", tcp->u_arg[1]);
1797#if 0
1798 else if (abbrev(tcp))
1799 printargc(", [/* %d arg%s */]", tcp, tcp->u_arg[1]);
1800#endif
1801 else {
1802 tprintf(", [");
1803 printargv(tcp, tcp->u_arg[1]);
1804 tprintf("]");
1805 }
1806 }
1807 return 0;
1808}
Dmitry V. Levinb9fe0112006-12-13 16:59:44 +00001809#endif /* SPARC || SPARC64 || SUNOS4 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001810
1811int
1812sys_execve(tcp)
1813struct tcb *tcp;
1814{
1815 if (entering(tcp)) {
1816 printpath(tcp, tcp->u_arg[0]);
1817 if (!verbose(tcp))
1818 tprintf(", %#lx", tcp->u_arg[1]);
1819#if 0
1820 else if (abbrev(tcp))
1821 printargc(", [/* %d arg%s */]", tcp, tcp->u_arg[1]);
1822#endif
1823 else {
1824 tprintf(", [");
1825 printargv(tcp, tcp->u_arg[1]);
1826 tprintf("]");
1827 }
1828 if (!verbose(tcp))
1829 tprintf(", %#lx", tcp->u_arg[2]);
1830 else if (abbrev(tcp))
1831 printargc(", [/* %d var%s */]", tcp, tcp->u_arg[2]);
1832 else {
1833 tprintf(", [");
1834 printargv(tcp, tcp->u_arg[2]);
1835 tprintf("]");
1836 }
1837 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001838 return 0;
1839}
1840
Roland McGrath5ef24ab2004-02-20 02:22:35 +00001841#if UNIXWARE > 2
John Hughes4e36a812001-04-18 15:11:51 +00001842
1843int sys_rexecve(tcp)
1844struct tcb *tcp;
1845{
1846 if (entering (tcp)) {
1847 sys_execve (tcp);
1848 tprintf (", %ld", tcp->u_arg[3]);
1849 }
1850 return 0;
1851}
1852
Roland McGrath5ef24ab2004-02-20 02:22:35 +00001853#endif
John Hughes4e36a812001-04-18 15:11:51 +00001854
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001855int
1856internal_exec(tcp)
1857struct tcb *tcp;
1858{
1859#ifdef SUNOS4
1860 if (exiting(tcp) && !syserror(tcp) && followfork)
1861 fixvfork(tcp);
1862#endif /* SUNOS4 */
Roland McGrathfdb097f2004-07-12 07:38:55 +00001863#if defined LINUX && defined TCB_WAITEXECVE
1864 if (exiting(tcp) && syserror(tcp))
1865 tcp->flags &= ~TCB_WAITEXECVE;
1866 else
1867 tcp->flags |= TCB_WAITEXECVE;
1868#endif /* LINUX && TCB_WAITEXECVE */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001869 return 0;
1870}
1871
1872#ifdef LINUX
Roland McGrath7ec1d352002-12-17 04:50:44 +00001873#ifndef __WNOTHREAD
1874#define __WNOTHREAD 0x20000000
1875#endif
1876#ifndef __WALL
1877#define __WALL 0x40000000
1878#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001879#ifndef __WCLONE
Roland McGrath7ec1d352002-12-17 04:50:44 +00001880#define __WCLONE 0x80000000
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001881#endif
1882#endif /* LINUX */
1883
Roland McGrathd9f816f2004-09-04 03:39:20 +00001884static const struct xlat wait4_options[] = {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001885 { WNOHANG, "WNOHANG" },
1886#ifndef WSTOPPED
1887 { WUNTRACED, "WUNTRACED" },
1888#endif
1889#ifdef WEXITED
1890 { WEXITED, "WEXITED" },
1891#endif
1892#ifdef WTRAPPED
1893 { WTRAPPED, "WTRAPPED" },
1894#endif
1895#ifdef WSTOPPED
1896 { WSTOPPED, "WSTOPPED" },
1897#endif
1898#ifdef WCONTINUED
1899 { WCONTINUED, "WCONTINUED" },
1900#endif
1901#ifdef WNOWAIT
1902 { WNOWAIT, "WNOWAIT" },
1903#endif
1904#ifdef __WCLONE
1905 { __WCLONE, "__WCLONE" },
1906#endif
Roland McGrath7ec1d352002-12-17 04:50:44 +00001907#ifdef __WALL
1908 { __WALL, "__WALL" },
1909#endif
1910#ifdef __WNOTHREAD
1911 { __WNOTHREAD, "__WNOTHREAD" },
1912#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001913 { 0, NULL },
1914};
1915
Roland McGrath5e02a572004-10-19 23:33:47 +00001916#if !defined WCOREFLAG && defined WCOREFLG
1917# define WCOREFLAG WCOREFLG
1918#endif
1919#ifndef WCOREFLAG
1920#define WCOREFLAG 0x80
1921#endif
1922
1923#ifndef W_STOPCODE
1924#define W_STOPCODE(sig) ((sig) << 8 | 0x7f)
1925#endif
1926#ifndef W_EXITCODE
1927#define W_EXITCODE(ret, sig) ((ret) << 8 | (sig))
1928#endif
1929
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001930static int
1931printstatus(status)
1932int status;
1933{
1934 int exited = 0;
1935
1936 /*
1937 * Here is a tricky presentation problem. This solution
1938 * is still not entirely satisfactory but since there
1939 * are no wait status constructors it will have to do.
1940 */
Roland McGrath79fbda52004-04-14 02:45:55 +00001941 if (WIFSTOPPED(status)) {
1942 tprintf("[{WIFSTOPPED(s) && WSTOPSIG(s) == %s}",
Nate Sammonsce780fc1999-03-29 23:23:13 +00001943 signame(WSTOPSIG(status)));
Roland McGrath79fbda52004-04-14 02:45:55 +00001944 status &= ~W_STOPCODE(WSTOPSIG(status));
1945 }
1946 else if (WIFSIGNALED(status)) {
1947 tprintf("[{WIFSIGNALED(s) && WTERMSIG(s) == %s%s}",
Nate Sammonsce780fc1999-03-29 23:23:13 +00001948 signame(WTERMSIG(status)),
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001949 WCOREDUMP(status) ? " && WCOREDUMP(s)" : "");
Roland McGrath79fbda52004-04-14 02:45:55 +00001950 status &= ~(W_EXITCODE(0, WTERMSIG(status)) | WCOREFLAG);
1951 }
1952 else if (WIFEXITED(status)) {
1953 tprintf("[{WIFEXITED(s) && WEXITSTATUS(s) == %d}",
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001954 WEXITSTATUS(status));
1955 exited = 1;
Roland McGrath79fbda52004-04-14 02:45:55 +00001956 status &= ~W_EXITCODE(WEXITSTATUS(status), 0);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001957 }
Roland McGrath79fbda52004-04-14 02:45:55 +00001958 else {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001959 tprintf("[%#x]", status);
Roland McGrath79fbda52004-04-14 02:45:55 +00001960 return 0;
1961 }
1962
1963 if (status == 0)
1964 tprintf("]");
1965 else
Roland McGrathf8cc83c2004-06-04 01:24:07 +00001966 tprintf(" | %#x]", status);
Roland McGrath79fbda52004-04-14 02:45:55 +00001967
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001968 return exited;
1969}
1970
1971static int
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00001972printwaitn(tcp, n, bitness)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001973struct tcb *tcp;
1974int n;
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00001975int bitness;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001976{
1977 int status;
1978 int exited = 0;
1979
1980 if (entering(tcp)) {
Roland McGrath5b63d962008-07-18 02:16:47 +00001981 /*
1982 * Sign-extend a 32-bit value when that's what it is.
1983 */
1984 long pid = tcp->u_arg[0];
1985 if (personality_wordsize[current_personality] < sizeof pid)
1986 pid = (long) (int) pid;
1987 tprintf("%ld, ", pid);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00001988 } else {
1989 /* status */
1990 if (!tcp->u_arg[1])
1991 tprintf("NULL");
1992 else if (syserror(tcp) || tcp->u_rval == 0)
1993 tprintf("%#lx", tcp->u_arg[1]);
1994 else if (umove(tcp, tcp->u_arg[1], &status) < 0)
1995 tprintf("[?]");
1996 else
1997 exited = printstatus(status);
1998 /* options */
1999 tprintf(", ");
Roland McGrathb2dee132005-06-01 19:02:36 +00002000 printflags(wait4_options, tcp->u_arg[2], "W???");
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002001 if (n == 4) {
2002 tprintf(", ");
2003 /* usage */
2004 if (!tcp->u_arg[3])
2005 tprintf("NULL");
2006#ifdef LINUX
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00002007 else if (tcp->u_rval > 0) {
2008#ifdef LINUX_64BIT
2009 if (bitness)
2010 printrusage32(tcp, tcp->u_arg[3]);
2011 else
2012#endif
2013 printrusage(tcp, tcp->u_arg[3]);
2014 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002015#endif /* LINUX */
2016#ifdef SUNOS4
2017 else if (tcp->u_rval > 0 && exited)
2018 printrusage(tcp, tcp->u_arg[3]);
2019#endif /* SUNOS4 */
2020 else
2021 tprintf("%#lx", tcp->u_arg[3]);
2022 }
2023 }
2024 return 0;
2025}
2026
2027int
Roland McGrathc74c0b72004-09-01 19:39:46 +00002028internal_wait(tcp, flagarg)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002029struct tcb *tcp;
Roland McGrathc74c0b72004-09-01 19:39:46 +00002030int flagarg;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002031{
Roland McGrathe85bbfe2003-01-09 06:53:31 +00002032 int got_kids;
2033
2034#ifdef TCB_CLONE_THREAD
2035 if (tcp->flags & TCB_CLONE_THREAD)
2036 /* The children we wait for are our parent's children. */
2037 got_kids = (tcp->parent->nchildren
2038 > tcp->parent->nclone_detached);
2039 else
2040 got_kids = (tcp->nchildren > tcp->nclone_detached);
2041#else
2042 got_kids = tcp->nchildren > 0;
2043#endif
2044
2045 if (entering(tcp) && got_kids) {
Roland McGrathb69f81b2002-12-21 23:25:18 +00002046 /* There are children that this parent should block for.
2047 But ptrace made us the parent of the traced children
2048 and the real parent will get ECHILD from the wait call.
2049
2050 XXX If we attached with strace -f -p PID, then there
2051 may be untraced dead children the parent could be reaping
2052 now, but we make him block. */
2053
2054 /* ??? WTA: fix bug with hanging children */
2055
Roland McGrathc74c0b72004-09-01 19:39:46 +00002056 if (!(tcp->u_arg[flagarg] & WNOHANG)) {
Roland McGrath09623452003-05-23 02:27:13 +00002057 /*
2058 * There are traced children. We'll make the parent
2059 * block to avoid a false ECHILD error due to our
2060 * ptrace having stolen the children. However,
2061 * we shouldn't block if there are zombies to reap.
2062 * XXX doesn't handle pgrp matches (u_arg[0]==0,<-1)
2063 */
Roland McGrathfccfb942003-10-01 21:59:44 +00002064 struct tcb *child = NULL;
Roland McGrath09623452003-05-23 02:27:13 +00002065 if (tcp->nzombies > 0 &&
2066 (tcp->u_arg[0] == -1 ||
Roland McGrathfccfb942003-10-01 21:59:44 +00002067 (child = pid2tcb(tcp->u_arg[0])) == NULL))
Roland McGrath09623452003-05-23 02:27:13 +00002068 return 0;
Roland McGrathfccfb942003-10-01 21:59:44 +00002069 if (tcp->u_arg[0] > 0) {
2070 /*
2071 * If the parent waits for a specified child
2072 * PID, then it must get ECHILD right away
2073 * if that PID is not one of its children.
2074 * Make sure that the requested PID matches
2075 * one of the parent's children that we are
2076 * tracing, and don't suspend it otherwise.
2077 */
2078 if (child == NULL)
2079 child = pid2tcb(tcp->u_arg[0]);
2080 if (child == NULL || child->parent != (
2081#ifdef TCB_CLONE_THREAD
2082 (tcp->flags & TCB_CLONE_THREAD)
2083 ? tcp->parent :
2084#endif
Roland McGrathd56a6562005-08-03 11:23:43 +00002085 tcp) ||
2086 (child->flags & TCB_EXITING))
Roland McGrathfccfb942003-10-01 21:59:44 +00002087 return 0;
2088 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002089 tcp->flags |= TCB_SUSPENDED;
2090 tcp->waitpid = tcp->u_arg[0];
Roland McGrathe85bbfe2003-01-09 06:53:31 +00002091#ifdef TCB_CLONE_THREAD
2092 if (tcp->flags & TCB_CLONE_THREAD)
2093 tcp->parent->nclone_waiting++;
2094#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002095 }
2096 }
Roland McGrathe85bbfe2003-01-09 06:53:31 +00002097 if (exiting(tcp) && tcp->u_error == ECHILD && got_kids) {
Roland McGrathc74c0b72004-09-01 19:39:46 +00002098 if (tcp->u_arg[flagarg] & WNOHANG) {
Roland McGrathb69f81b2002-12-21 23:25:18 +00002099 /* We must force a fake result of 0 instead of
2100 the ECHILD error. */
2101 extern int force_result();
2102 return force_result(tcp, 0, 0);
2103 }
Roland McGrathb69f81b2002-12-21 23:25:18 +00002104 }
Roland McGrath09623452003-05-23 02:27:13 +00002105 else if (exiting(tcp) && tcp->u_error == 0 && tcp->u_rval > 0 &&
2106 tcp->nzombies > 0 && pid2tcb(tcp->u_rval) == NULL) {
2107 /*
2108 * We just reaped a child we don't know about,
2109 * presumably a zombie we already droptcb'd.
2110 */
2111 tcp->nzombies--;
2112 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002113 return 0;
2114}
2115
2116#ifdef SVR4
2117
2118int
2119sys_wait(tcp)
2120struct tcb *tcp;
2121{
2122 if (exiting(tcp)) {
2123 /* The library wrapper stuffs this into the user variable. */
2124 if (!syserror(tcp))
2125 printstatus(getrval2(tcp));
2126 }
2127 return 0;
2128}
2129
2130#endif /* SVR4 */
2131
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002132#ifdef FREEBSD
2133int
2134sys_wait(tcp)
2135struct tcb *tcp;
2136{
2137 int status;
Roland McGrath5a223472002-12-15 23:58:26 +00002138
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002139 if (exiting(tcp)) {
2140 if (!syserror(tcp)) {
2141 if (umove(tcp, tcp->u_arg[0], &status) < 0)
2142 tprintf("%#lx", tcp->u_arg[0]);
2143 else
2144 printstatus(status);
2145 }
2146 }
2147 return 0;
2148}
2149#endif
2150
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002151int
2152sys_waitpid(tcp)
2153struct tcb *tcp;
2154{
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00002155 return printwaitn(tcp, 3, 0);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002156}
2157
2158int
2159sys_wait4(tcp)
2160struct tcb *tcp;
2161{
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00002162 return printwaitn(tcp, 4, 0);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002163}
2164
Wichert Akkermanf5eeabb1999-11-18 17:09:47 +00002165#ifdef ALPHA
2166int
2167sys_osf_wait4(tcp)
2168struct tcb *tcp;
2169{
2170 return printwaitn(tcp, 4, 1);
2171}
2172#endif
2173
Roland McGrathc74c0b72004-09-01 19:39:46 +00002174#if defined SVR4 || defined LINUX
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002175
Roland McGrathd9f816f2004-09-04 03:39:20 +00002176static const struct xlat waitid_types[] = {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002177 { P_PID, "P_PID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002178#ifdef P_PPID
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002179 { P_PPID, "P_PPID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002180#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002181 { P_PGID, "P_PGID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002182#ifdef P_SID
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002183 { P_SID, "P_SID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002184#endif
2185#ifdef P_CID
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002186 { P_CID, "P_CID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002187#endif
2188#ifdef P_UID
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002189 { P_UID, "P_UID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002190#endif
2191#ifdef P_GID
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002192 { P_GID, "P_GID" },
Roland McGrathc74c0b72004-09-01 19:39:46 +00002193#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002194 { P_ALL, "P_ALL" },
2195#ifdef P_LWPID
2196 { P_LWPID, "P_LWPID" },
2197#endif
2198 { 0, NULL },
2199};
2200
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002201int
2202sys_waitid(tcp)
2203struct tcb *tcp;
2204{
2205 siginfo_t si;
2206 int exited;
2207
2208 if (entering(tcp)) {
2209 printxval(waitid_types, tcp->u_arg[0], "P_???");
2210 tprintf(", %ld, ", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002211 }
2212 else {
2213 /* siginfo */
2214 exited = 0;
2215 if (!tcp->u_arg[2])
2216 tprintf("NULL");
2217 else if (syserror(tcp))
2218 tprintf("%#lx", tcp->u_arg[2]);
2219 else if (umove(tcp, tcp->u_arg[2], &si) < 0)
2220 tprintf("{???}");
2221 else
Denys Vlasenkof535b542009-01-13 18:30:55 +00002222 printsiginfo(&si, verbose(tcp));
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002223 /* options */
2224 tprintf(", ");
Roland McGrathb2dee132005-06-01 19:02:36 +00002225 printflags(wait4_options, tcp->u_arg[3], "W???");
Roland McGrath39426a32004-10-06 22:02:59 +00002226 if (tcp->u_nargs > 4) {
2227 /* usage */
2228 tprintf(", ");
2229 if (!tcp->u_arg[4])
2230 tprintf("NULL");
2231 else if (tcp->u_error)
2232 tprintf("%#lx", tcp->u_arg[4]);
2233 else
2234 printrusage(tcp, tcp->u_arg[4]);
2235 }
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002236 }
2237 return 0;
2238}
2239
Roland McGrathc74c0b72004-09-01 19:39:46 +00002240#endif /* SVR4 or LINUX */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002241
2242int
2243sys_alarm(tcp)
2244struct tcb *tcp;
2245{
2246 if (entering(tcp))
2247 tprintf("%lu", tcp->u_arg[0]);
2248 return 0;
2249}
2250
2251int
2252sys_uname(tcp)
2253struct tcb *tcp;
2254{
2255 struct utsname uname;
2256
2257 if (exiting(tcp)) {
2258 if (syserror(tcp) || !verbose(tcp))
2259 tprintf("%#lx", tcp->u_arg[0]);
2260 else if (umove(tcp, tcp->u_arg[0], &uname) < 0)
2261 tprintf("{...}");
2262 else if (!abbrev(tcp)) {
2263
2264 tprintf("{sysname=\"%s\", nodename=\"%s\", ",
2265 uname.sysname, uname.nodename);
2266 tprintf("release=\"%s\", version=\"%s\", ",
2267 uname.release, uname.version);
2268 tprintf("machine=\"%s\"", uname.machine);
2269#ifdef LINUX
2270#ifndef __GLIBC__
2271 tprintf(", domainname=\"%s\"", uname.domainname);
2272#endif /* __GLIBC__ */
2273#endif /* LINUX */
2274 tprintf("}");
2275 }
2276 else
2277 tprintf("{sys=\"%s\", node=\"%s\", ...}",
2278 uname.sysname, uname.nodename);
2279 }
2280 return 0;
2281}
2282
2283#ifndef SVR4
2284
Roland McGrathd9f816f2004-09-04 03:39:20 +00002285static const struct xlat ptrace_cmds[] = {
Roland McGrath5a223472002-12-15 23:58:26 +00002286#ifndef FREEBSD
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002287 { PTRACE_TRACEME, "PTRACE_TRACEME" },
2288 { PTRACE_PEEKTEXT, "PTRACE_PEEKTEXT", },
2289 { PTRACE_PEEKDATA, "PTRACE_PEEKDATA", },
2290 { PTRACE_PEEKUSER, "PTRACE_PEEKUSER", },
2291 { PTRACE_POKETEXT, "PTRACE_POKETEXT", },
2292 { PTRACE_POKEDATA, "PTRACE_POKEDATA", },
2293 { PTRACE_POKEUSER, "PTRACE_POKEUSER", },
2294 { PTRACE_CONT, "PTRACE_CONT" },
2295 { PTRACE_KILL, "PTRACE_KILL" },
2296 { PTRACE_SINGLESTEP, "PTRACE_SINGLESTEP" },
2297 { PTRACE_ATTACH, "PTRACE_ATTACH" },
2298 { PTRACE_DETACH, "PTRACE_DETACH" },
Roland McGrathbf621d42003-01-14 09:46:21 +00002299#ifdef PTRACE_GETREGS
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002300 { PTRACE_GETREGS, "PTRACE_GETREGS" },
Roland McGrathbf621d42003-01-14 09:46:21 +00002301#endif
2302#ifdef PTRACE_SETREGS
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002303 { PTRACE_SETREGS, "PTRACE_SETREGS" },
Roland McGrathbf621d42003-01-14 09:46:21 +00002304#endif
2305#ifdef PTRACE_GETFPREGS
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002306 { PTRACE_GETFPREGS, "PTRACE_GETFPREGS", },
Roland McGrathbf621d42003-01-14 09:46:21 +00002307#endif
2308#ifdef PTRACE_SETFPREGS
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002309 { PTRACE_SETFPREGS, "PTRACE_SETFPREGS", },
Roland McGrathbf621d42003-01-14 09:46:21 +00002310#endif
2311#ifdef PTRACE_GETFPXREGS
2312 { PTRACE_GETFPXREGS, "PTRACE_GETFPXREGS", },
2313#endif
2314#ifdef PTRACE_SETFPXREGS
2315 { PTRACE_SETFPXREGS, "PTRACE_SETFPXREGS", },
2316#endif
Roland McGrathf04bb482005-05-09 07:45:33 +00002317#ifdef PTRACE_GETVRREGS
2318 { PTRACE_GETVRREGS, "PTRACE_GETVRREGS", },
2319#endif
2320#ifdef PTRACE_SETVRREGS
2321 { PTRACE_SETVRREGS, "PTRACE_SETVRREGS", },
2322#endif
Denys Vlasenkof535b542009-01-13 18:30:55 +00002323#ifdef PTRACE_SETOPTIONS
2324 { PTRACE_SETOPTIONS, "PTRACE_SETOPTIONS", },
2325#endif
2326#ifdef PTRACE_GETEVENTMSG
2327 { PTRACE_GETEVENTMSG, "PTRACE_GETEVENTMSG", },
2328#endif
2329#ifdef PTRACE_GETSIGINFO
2330 { PTRACE_GETSIGINFO, "PTRACE_GETSIGINFO", },
2331#endif
2332#ifdef PTRACE_SETSIGINFO
2333 { PTRACE_SETSIGINFO, "PTRACE_SETSIGINFO", },
2334#endif
Roland McGrathbf621d42003-01-14 09:46:21 +00002335#ifdef SUNOS4
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002336 { PTRACE_READDATA, "PTRACE_READDATA" },
2337 { PTRACE_WRITEDATA, "PTRACE_WRITEDATA" },
2338 { PTRACE_READTEXT, "PTRACE_READTEXT" },
2339 { PTRACE_WRITETEXT, "PTRACE_WRITETEXT" },
2340 { PTRACE_GETFPAREGS, "PTRACE_GETFPAREGS" },
2341 { PTRACE_SETFPAREGS, "PTRACE_SETFPAREGS" },
2342#ifdef SPARC
2343 { PTRACE_GETWINDOW, "PTRACE_GETWINDOW" },
2344 { PTRACE_SETWINDOW, "PTRACE_SETWINDOW" },
2345#else /* !SPARC */
2346 { PTRACE_22, "PTRACE_PTRACE_22" },
2347 { PTRACE_23, "PTRACE_PTRACE_23" },
2348#endif /* !SPARC */
2349#endif /* SUNOS4 */
2350 { PTRACE_SYSCALL, "PTRACE_SYSCALL" },
2351#ifdef SUNOS4
2352 { PTRACE_DUMPCORE, "PTRACE_DUMPCORE" },
2353#ifdef I386
2354 { PTRACE_SETWRBKPT, "PTRACE_SETWRBKPT" },
2355 { PTRACE_SETACBKPT, "PTRACE_SETACBKPT" },
2356 { PTRACE_CLRDR7, "PTRACE_CLRDR7" },
2357#else /* !I386 */
2358 { PTRACE_26, "PTRACE_26" },
2359 { PTRACE_27, "PTRACE_27" },
2360 { PTRACE_28, "PTRACE_28" },
2361#endif /* !I386 */
2362 { PTRACE_GETUCODE, "PTRACE_GETUCODE" },
2363#endif /* SUNOS4 */
Denys Vlasenkof535b542009-01-13 18:30:55 +00002364
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002365#else /* FREEBSD */
Denys Vlasenkof535b542009-01-13 18:30:55 +00002366
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002367 { PT_TRACE_ME, "PT_TRACE_ME" },
2368 { PT_READ_I, "PT_READ_I" },
2369 { PT_READ_D, "PT_READ_D" },
2370 { PT_WRITE_I, "PT_WRITE_I" },
2371 { PT_WRITE_D, "PT_WRITE_D" },
John Hughesa2278142001-09-28 16:21:30 +00002372#ifdef PT_READ_U
2373 { PT_READ_U, "PT_READ_U" },
2374#endif
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002375 { PT_CONTINUE, "PT_CONTINUE" },
2376 { PT_KILL, "PT_KILL" },
2377 { PT_STEP, "PT_STEP" },
2378 { PT_ATTACH, "PT_ATTACH" },
2379 { PT_DETACH, "PT_DETACH" },
2380 { PT_GETREGS, "PT_GETREGS" },
2381 { PT_SETREGS, "PT_SETREGS" },
2382 { PT_GETFPREGS, "PT_GETFPREGS" },
2383 { PT_SETFPREGS, "PT_SETFPREGS" },
2384 { PT_GETDBREGS, "PT_GETDBREGS" },
2385 { PT_SETDBREGS, "PT_SETDBREGS" },
2386#endif /* FREEBSD */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002387 { 0, NULL },
2388};
2389
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00002390#ifndef FREEBSD
Denys Vlasenkof535b542009-01-13 18:30:55 +00002391#ifdef PTRACE_SETOPTIONS
2392static const struct xlat ptrace_setoptions_flags[] = {
2393#ifdef PTRACE_O_TRACESYSGOOD
2394 { PTRACE_O_TRACESYSGOOD,"PTRACE_O_TRACESYSGOOD" },
2395#endif
2396#ifdef PTRACE_O_TRACEFORK
2397 { PTRACE_O_TRACEFORK, "PTRACE_O_TRACEFORK" },
2398#endif
2399#ifdef PTRACE_O_TRACEVFORK
2400 { PTRACE_O_TRACEVFORK, "PTRACE_O_TRACEVFORK" },
2401#endif
2402#ifdef PTRACE_O_TRACECLONE
2403 { PTRACE_O_TRACECLONE, "PTRACE_O_TRACECLONE" },
2404#endif
2405#ifdef PTRACE_O_TRACEEXEC
2406 { PTRACE_O_TRACEEXEC, "PTRACE_O_TRACEEXEC" },
2407#endif
2408#ifdef PTRACE_O_TRACEVFORKDONE
2409 { PTRACE_O_TRACEVFORKDONE,"PTRACE_O_TRACEVFORKDONE"},
2410#endif
2411#ifdef PTRACE_O_TRACEEXIT
2412 { PTRACE_O_TRACEEXIT, "PTRACE_O_TRACEEXIT" },
2413#endif
2414 { 0, NULL },
2415};
2416#endif
2417#endif
2418
2419#ifndef FREEBSD
Roland McGrathd9f816f2004-09-04 03:39:20 +00002420const struct xlat struct_user_offsets[] = {
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002421#ifdef LINUX
Michal Ludvig10a88d02002-10-07 14:31:00 +00002422#if defined(S390) || defined(S390X)
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00002423 { PT_PSWMASK, "psw_mask" },
2424 { PT_PSWADDR, "psw_addr" },
2425 { PT_GPR0, "gpr0" },
2426 { PT_GPR1, "gpr1" },
2427 { PT_GPR2, "gpr2" },
2428 { PT_GPR3, "gpr3" },
2429 { PT_GPR4, "gpr4" },
2430 { PT_GPR5, "gpr5" },
2431 { PT_GPR6, "gpr6" },
2432 { PT_GPR7, "gpr7" },
2433 { PT_GPR8, "gpr8" },
2434 { PT_GPR9, "gpr9" },
2435 { PT_GPR10, "gpr10" },
2436 { PT_GPR11, "gpr11" },
2437 { PT_GPR12, "gpr12" },
2438 { PT_GPR13, "gpr13" },
2439 { PT_GPR14, "gpr14" },
2440 { PT_GPR15, "gpr15" },
2441 { PT_ACR0, "acr0" },
2442 { PT_ACR1, "acr1" },
2443 { PT_ACR2, "acr2" },
2444 { PT_ACR3, "acr3" },
2445 { PT_ACR4, "acr4" },
2446 { PT_ACR5, "acr5" },
2447 { PT_ACR6, "acr6" },
2448 { PT_ACR7, "acr7" },
2449 { PT_ACR8, "acr8" },
2450 { PT_ACR9, "acr9" },
2451 { PT_ACR10, "acr10" },
2452 { PT_ACR11, "acr11" },
2453 { PT_ACR12, "acr12" },
2454 { PT_ACR13, "acr13" },
2455 { PT_ACR14, "acr14" },
2456 { PT_ACR15, "acr15" },
2457 { PT_ORIGGPR2, "orig_gpr2" },
2458 { PT_FPC, "fpc" },
Michal Ludvig10a88d02002-10-07 14:31:00 +00002459#if defined(S390)
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00002460 { PT_FPR0_HI, "fpr0.hi" },
2461 { PT_FPR0_LO, "fpr0.lo" },
2462 { PT_FPR1_HI, "fpr1.hi" },
2463 { PT_FPR1_LO, "fpr1.lo" },
2464 { PT_FPR2_HI, "fpr2.hi" },
2465 { PT_FPR2_LO, "fpr2.lo" },
2466 { PT_FPR3_HI, "fpr3.hi" },
2467 { PT_FPR3_LO, "fpr3.lo" },
2468 { PT_FPR4_HI, "fpr4.hi" },
2469 { PT_FPR4_LO, "fpr4.lo" },
2470 { PT_FPR5_HI, "fpr5.hi" },
2471 { PT_FPR5_LO, "fpr5.lo" },
2472 { PT_FPR6_HI, "fpr6.hi" },
2473 { PT_FPR6_LO, "fpr6.lo" },
2474 { PT_FPR7_HI, "fpr7.hi" },
2475 { PT_FPR7_LO, "fpr7.lo" },
2476 { PT_FPR8_HI, "fpr8.hi" },
2477 { PT_FPR8_LO, "fpr8.lo" },
2478 { PT_FPR9_HI, "fpr9.hi" },
2479 { PT_FPR9_LO, "fpr9.lo" },
2480 { PT_FPR10_HI, "fpr10.hi" },
2481 { PT_FPR10_LO, "fpr10.lo" },
2482 { PT_FPR11_HI, "fpr11.hi" },
2483 { PT_FPR11_LO, "fpr11.lo" },
2484 { PT_FPR12_HI, "fpr12.hi" },
2485 { PT_FPR12_LO, "fpr12.lo" },
2486 { PT_FPR13_HI, "fpr13.hi" },
2487 { PT_FPR13_LO, "fpr13.lo" },
2488 { PT_FPR14_HI, "fpr14.hi" },
2489 { PT_FPR14_LO, "fpr14.lo" },
2490 { PT_FPR15_HI, "fpr15.hi" },
2491 { PT_FPR15_LO, "fpr15.lo" },
Michal Ludvig10a88d02002-10-07 14:31:00 +00002492#endif
2493#if defined(S390X)
2494 { PT_FPR0, "fpr0" },
2495 { PT_FPR1, "fpr1" },
2496 { PT_FPR2, "fpr2" },
2497 { PT_FPR3, "fpr3" },
2498 { PT_FPR4, "fpr4" },
2499 { PT_FPR5, "fpr5" },
2500 { PT_FPR6, "fpr6" },
2501 { PT_FPR7, "fpr7" },
2502 { PT_FPR8, "fpr8" },
2503 { PT_FPR9, "fpr9" },
2504 { PT_FPR10, "fpr10" },
2505 { PT_FPR11, "fpr11" },
2506 { PT_FPR12, "fpr12" },
2507 { PT_FPR13, "fpr13" },
2508 { PT_FPR14, "fpr14" },
2509 { PT_FPR15, "fpr15" },
2510#endif
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00002511 { PT_CR_9, "cr9" },
2512 { PT_CR_10, "cr10" },
2513 { PT_CR_11, "cr11" },
Michal Ludvig10a88d02002-10-07 14:31:00 +00002514 { PT_IEEE_IP, "ieee_exception_ip" },
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00002515#endif
2516#if defined(SPARC)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002517 /* XXX No support for these offsets yet. */
Wichert Akkermanc1652e22001-03-27 12:17:16 +00002518#elif defined(HPPA)
2519 /* XXX No support for these offsets yet. */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002520#elif defined(POWERPC)
Roland McGrath5a223472002-12-15 23:58:26 +00002521#ifndef PT_ORIG_R3
2522#define PT_ORIG_R3 34
2523#endif
Roland McGratheb285352003-01-14 09:59:00 +00002524#define REGSIZE (sizeof(unsigned long))
2525 { REGSIZE*PT_R0, "r0" },
2526 { REGSIZE*PT_R1, "r1" },
2527 { REGSIZE*PT_R2, "r2" },
2528 { REGSIZE*PT_R3, "r3" },
2529 { REGSIZE*PT_R4, "r4" },
2530 { REGSIZE*PT_R5, "r5" },
2531 { REGSIZE*PT_R6, "r6" },
2532 { REGSIZE*PT_R7, "r7" },
2533 { REGSIZE*PT_R8, "r8" },
2534 { REGSIZE*PT_R9, "r9" },
2535 { REGSIZE*PT_R10, "r10" },
2536 { REGSIZE*PT_R11, "r11" },
2537 { REGSIZE*PT_R12, "r12" },
2538 { REGSIZE*PT_R13, "r13" },
2539 { REGSIZE*PT_R14, "r14" },
2540 { REGSIZE*PT_R15, "r15" },
2541 { REGSIZE*PT_R16, "r16" },
2542 { REGSIZE*PT_R17, "r17" },
2543 { REGSIZE*PT_R18, "r18" },
2544 { REGSIZE*PT_R19, "r19" },
2545 { REGSIZE*PT_R20, "r20" },
2546 { REGSIZE*PT_R21, "r21" },
2547 { REGSIZE*PT_R22, "r22" },
2548 { REGSIZE*PT_R23, "r23" },
2549 { REGSIZE*PT_R24, "r24" },
2550 { REGSIZE*PT_R25, "r25" },
2551 { REGSIZE*PT_R26, "r26" },
2552 { REGSIZE*PT_R27, "r27" },
2553 { REGSIZE*PT_R28, "r28" },
2554 { REGSIZE*PT_R29, "r29" },
2555 { REGSIZE*PT_R30, "r30" },
2556 { REGSIZE*PT_R31, "r31" },
2557 { REGSIZE*PT_NIP, "NIP" },
2558 { REGSIZE*PT_MSR, "MSR" },
2559 { REGSIZE*PT_ORIG_R3, "ORIG_R3" },
2560 { REGSIZE*PT_CTR, "CTR" },
2561 { REGSIZE*PT_LNK, "LNK" },
2562 { REGSIZE*PT_XER, "XER" },
2563 { REGSIZE*PT_CCR, "CCR" },
2564 { REGSIZE*PT_FPR0, "FPR0" },
2565#undef REGSIZE
Roland McGrath5a223472002-12-15 23:58:26 +00002566#else
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002567#ifdef ALPHA
Wichert Akkerman4dc8a2a1999-12-23 14:20:14 +00002568 { 0, "r0" },
2569 { 1, "r1" },
2570 { 2, "r2" },
2571 { 3, "r3" },
2572 { 4, "r4" },
2573 { 5, "r5" },
2574 { 6, "r6" },
2575 { 7, "r7" },
2576 { 8, "r8" },
2577 { 9, "r9" },
2578 { 10, "r10" },
2579 { 11, "r11" },
2580 { 12, "r12" },
2581 { 13, "r13" },
2582 { 14, "r14" },
2583 { 15, "r15" },
2584 { 16, "r16" },
2585 { 17, "r17" },
2586 { 18, "r18" },
2587 { 19, "r19" },
2588 { 20, "r20" },
2589 { 21, "r21" },
2590 { 22, "r22" },
2591 { 23, "r23" },
2592 { 24, "r24" },
2593 { 25, "r25" },
2594 { 26, "r26" },
2595 { 27, "r27" },
2596 { 28, "r28" },
2597 { 29, "gp" },
2598 { 30, "fp" },
2599 { 31, "zero" },
2600 { 32, "fp0" },
2601 { 33, "fp" },
2602 { 34, "fp2" },
2603 { 35, "fp3" },
2604 { 36, "fp4" },
2605 { 37, "fp5" },
2606 { 38, "fp6" },
2607 { 39, "fp7" },
2608 { 40, "fp8" },
2609 { 41, "fp9" },
2610 { 42, "fp10" },
2611 { 43, "fp11" },
2612 { 44, "fp12" },
2613 { 45, "fp13" },
2614 { 46, "fp14" },
2615 { 47, "fp15" },
2616 { 48, "fp16" },
2617 { 49, "fp17" },
2618 { 50, "fp18" },
2619 { 51, "fp19" },
2620 { 52, "fp20" },
2621 { 53, "fp21" },
2622 { 54, "fp22" },
2623 { 55, "fp23" },
2624 { 56, "fp24" },
2625 { 57, "fp25" },
2626 { 58, "fp26" },
2627 { 59, "fp27" },
2628 { 60, "fp28" },
2629 { 61, "fp29" },
2630 { 62, "fp30" },
2631 { 63, "fp31" },
2632 { 64, "pc" },
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002633#else /* !ALPHA */
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00002634#ifdef IA64
2635 { PT_F32, "f32" }, { PT_F33, "f33" }, { PT_F34, "f34" },
2636 { PT_F35, "f35" }, { PT_F36, "f36" }, { PT_F37, "f37" },
2637 { PT_F38, "f38" }, { PT_F39, "f39" }, { PT_F40, "f40" },
2638 { PT_F41, "f41" }, { PT_F42, "f42" }, { PT_F43, "f43" },
2639 { PT_F44, "f44" }, { PT_F45, "f45" }, { PT_F46, "f46" },
2640 { PT_F47, "f47" }, { PT_F48, "f48" }, { PT_F49, "f49" },
2641 { PT_F50, "f50" }, { PT_F51, "f51" }, { PT_F52, "f52" },
2642 { PT_F53, "f53" }, { PT_F54, "f54" }, { PT_F55, "f55" },
2643 { PT_F56, "f56" }, { PT_F57, "f57" }, { PT_F58, "f58" },
2644 { PT_F59, "f59" }, { PT_F60, "f60" }, { PT_F61, "f61" },
2645 { PT_F62, "f62" }, { PT_F63, "f63" }, { PT_F64, "f64" },
2646 { PT_F65, "f65" }, { PT_F66, "f66" }, { PT_F67, "f67" },
2647 { PT_F68, "f68" }, { PT_F69, "f69" }, { PT_F70, "f70" },
2648 { PT_F71, "f71" }, { PT_F72, "f72" }, { PT_F73, "f73" },
2649 { PT_F74, "f74" }, { PT_F75, "f75" }, { PT_F76, "f76" },
2650 { PT_F77, "f77" }, { PT_F78, "f78" }, { PT_F79, "f79" },
2651 { PT_F80, "f80" }, { PT_F81, "f81" }, { PT_F82, "f82" },
2652 { PT_F83, "f83" }, { PT_F84, "f84" }, { PT_F85, "f85" },
2653 { PT_F86, "f86" }, { PT_F87, "f87" }, { PT_F88, "f88" },
2654 { PT_F89, "f89" }, { PT_F90, "f90" }, { PT_F91, "f91" },
2655 { PT_F92, "f92" }, { PT_F93, "f93" }, { PT_F94, "f94" },
2656 { PT_F95, "f95" }, { PT_F96, "f96" }, { PT_F97, "f97" },
2657 { PT_F98, "f98" }, { PT_F99, "f99" }, { PT_F100, "f100" },
2658 { PT_F101, "f101" }, { PT_F102, "f102" }, { PT_F103, "f103" },
2659 { PT_F104, "f104" }, { PT_F105, "f105" }, { PT_F106, "f106" },
2660 { PT_F107, "f107" }, { PT_F108, "f108" }, { PT_F109, "f109" },
2661 { PT_F110, "f110" }, { PT_F111, "f111" }, { PT_F112, "f112" },
2662 { PT_F113, "f113" }, { PT_F114, "f114" }, { PT_F115, "f115" },
2663 { PT_F116, "f116" }, { PT_F117, "f117" }, { PT_F118, "f118" },
2664 { PT_F119, "f119" }, { PT_F120, "f120" }, { PT_F121, "f121" },
2665 { PT_F122, "f122" }, { PT_F123, "f123" }, { PT_F124, "f124" },
2666 { PT_F125, "f125" }, { PT_F126, "f126" }, { PT_F127, "f127" },
2667 /* switch stack: */
2668 { PT_F2, "f2" }, { PT_F3, "f3" }, { PT_F4, "f4" },
2669 { PT_F5, "f5" }, { PT_F10, "f10" }, { PT_F11, "f11" },
2670 { PT_F12, "f12" }, { PT_F13, "f13" }, { PT_F14, "f14" },
2671 { PT_F15, "f15" }, { PT_F16, "f16" }, { PT_F17, "f17" },
2672 { PT_F18, "f18" }, { PT_F19, "f19" }, { PT_F20, "f20" },
2673 { PT_F21, "f21" }, { PT_F22, "f22" }, { PT_F23, "f23" },
2674 { PT_F24, "f24" }, { PT_F25, "f25" }, { PT_F26, "f26" },
2675 { PT_F27, "f27" }, { PT_F28, "f28" }, { PT_F29, "f29" },
2676 { PT_F30, "f30" }, { PT_F31, "f31" }, { PT_R4, "r4" },
2677 { PT_R5, "r5" }, { PT_R6, "r6" }, { PT_R7, "r7" },
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00002678 { PT_B1, "b1" }, { PT_B2, "b2" }, { PT_B3, "b3" },
2679 { PT_B4, "b4" }, { PT_B5, "b5" },
Roland McGrathca4e10c2004-01-13 10:13:20 +00002680 { PT_AR_EC, "ar.ec" }, { PT_AR_LC, "ar.lc" },
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00002681 /* pt_regs */
Roland McGrathca4e10c2004-01-13 10:13:20 +00002682 { PT_CR_IPSR, "psr" }, { PT_CR_IIP, "ip" },
2683 { PT_CFM, "cfm" }, { PT_AR_UNAT, "ar.unat" },
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00002684 { PT_AR_PFS, "ar.pfs" }, { PT_AR_RSC, "ar.rsc" },
2685 { PT_AR_RNAT, "ar.rnat" }, { PT_AR_BSPSTORE, "ar.bspstore" },
2686 { PT_PR, "pr" }, { PT_B6, "b6" }, { PT_AR_BSP, "ar.bsp" },
2687 { PT_R1, "r1" }, { PT_R2, "r2" }, { PT_R3, "r3" },
2688 { PT_R12, "r12" }, { PT_R13, "r13" }, { PT_R14, "r14" },
2689 { PT_R15, "r15" }, { PT_R8, "r8" }, { PT_R9, "r9" },
2690 { PT_R10, "r10" }, { PT_R11, "r11" }, { PT_R16, "r16" },
2691 { PT_R17, "r17" }, { PT_R18, "r18" }, { PT_R19, "r19" },
2692 { PT_R20, "r20" }, { PT_R21, "r21" }, { PT_R22, "r22" },
2693 { PT_R23, "r23" }, { PT_R24, "r24" }, { PT_R25, "r25" },
2694 { PT_R26, "r26" }, { PT_R27, "r27" }, { PT_R28, "r28" },
2695 { PT_R29, "r29" }, { PT_R30, "r30" }, { PT_R31, "r31" },
2696 { PT_AR_CCV, "ar.ccv" }, { PT_AR_FPSR, "ar.fpsr" },
2697 { PT_B0, "b0" }, { PT_B7, "b7" }, { PT_F6, "f6" },
2698 { PT_F7, "f7" }, { PT_F8, "f8" }, { PT_F9, "f9" },
Roland McGrathfb1bc072004-03-01 21:29:24 +00002699# ifdef PT_AR_CSD
2700 { PT_AR_CSD, "ar.csd" },
2701# endif
2702# ifdef PT_AR_SSD
2703 { PT_AR_SSD, "ar.ssd" },
2704# endif
Roland McGrathca4e10c2004-01-13 10:13:20 +00002705 { PT_DBR, "dbr" }, { PT_IBR, "ibr" }, { PT_PMD, "pmd" },
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00002706#else /* !IA64 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002707#ifdef I386
2708 { 4*EBX, "4*EBX" },
2709 { 4*ECX, "4*ECX" },
2710 { 4*EDX, "4*EDX" },
2711 { 4*ESI, "4*ESI" },
2712 { 4*EDI, "4*EDI" },
2713 { 4*EBP, "4*EBP" },
2714 { 4*EAX, "4*EAX" },
2715 { 4*DS, "4*DS" },
2716 { 4*ES, "4*ES" },
2717 { 4*FS, "4*FS" },
2718 { 4*GS, "4*GS" },
2719 { 4*ORIG_EAX, "4*ORIG_EAX" },
2720 { 4*EIP, "4*EIP" },
2721 { 4*CS, "4*CS" },
2722 { 4*EFL, "4*EFL" },
2723 { 4*UESP, "4*UESP" },
2724 { 4*SS, "4*SS" },
2725#else /* !I386 */
Michal Ludvig0e035502002-09-23 15:41:01 +00002726#ifdef X86_64
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002727 { 8*R15, "8*R15" },
2728 { 8*R14, "8*R14" },
2729 { 8*R13, "8*R13" },
2730 { 8*R12, "8*R12" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002731 { 8*RBP, "8*RBP" },
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002732 { 8*RBX, "8*RBX" },
2733 { 8*R11, "8*R11" },
2734 { 8*R10, "8*R10" },
2735 { 8*R9, "8*R9" },
2736 { 8*R8, "8*R8" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002737 { 8*RAX, "8*RAX" },
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002738 { 8*RCX, "8*RCX" },
2739 { 8*RDX, "8*RDX" },
2740 { 8*RSI, "8*RSI" },
2741 { 8*RDI, "8*RDI" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002742#if 0
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002743 { DS, "DS" },
2744 { ES, "ES" },
2745 { FS, "FS" },
2746 { GS, "GS" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002747#endif
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002748 { 8*ORIG_RAX, "8*ORIG_RAX" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002749 { 8*RIP, "8*RIP" },
2750 { 8*CS, "8*CS" },
2751 { 8*EFLAGS, "8*EFL" },
Roland McGratha4f9f2d2005-06-07 23:21:20 +00002752 { 8*RSP, "8*RSP" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002753 { 8*SS, "8*SS" },
Michal Ludvig0e035502002-09-23 15:41:01 +00002754#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00002755#ifdef M68K
2756 { 4*PT_D1, "4*PT_D1" },
2757 { 4*PT_D2, "4*PT_D2" },
2758 { 4*PT_D3, "4*PT_D3" },
2759 { 4*PT_D4, "4*PT_D4" },
2760 { 4*PT_D5, "4*PT_D5" },
2761 { 4*PT_D6, "4*PT_D6" },
2762 { 4*PT_D7, "4*PT_D7" },
2763 { 4*PT_A0, "4*PT_A0" },
2764 { 4*PT_A1, "4*PT_A1" },
2765 { 4*PT_A2, "4*PT_A2" },
2766 { 4*PT_A3, "4*PT_A3" },
2767 { 4*PT_A4, "4*PT_A4" },
2768 { 4*PT_A5, "4*PT_A5" },
2769 { 4*PT_A6, "4*PT_A6" },
2770 { 4*PT_D0, "4*PT_D0" },
2771 { 4*PT_USP, "4*PT_USP" },
2772 { 4*PT_ORIG_D0, "4*PT_ORIG_D0" },
2773 { 4*PT_SR, "4*PT_SR" },
2774 { 4*PT_PC, "4*PT_PC" },
2775#endif /* M68K */
2776#endif /* !I386 */
Wichert Akkermanccef6372002-05-01 16:39:22 +00002777#ifdef SH
Denys Vlasenkoadedb512008-12-30 18:47:55 +00002778 { 4*REG_REG0, "4*REG_REG0" },
2779 { 4*(REG_REG0+1), "4*REG_REG1" },
2780 { 4*(REG_REG0+2), "4*REG_REG2" },
2781 { 4*(REG_REG0+3), "4*REG_REG3" },
2782 { 4*(REG_REG0+4), "4*REG_REG4" },
2783 { 4*(REG_REG0+5), "4*REG_REG5" },
2784 { 4*(REG_REG0+6), "4*REG_REG6" },
2785 { 4*(REG_REG0+7), "4*REG_REG7" },
2786 { 4*(REG_REG0+8), "4*REG_REG8" },
2787 { 4*(REG_REG0+9), "4*REG_REG9" },
2788 { 4*(REG_REG0+10), "4*REG_REG10" },
2789 { 4*(REG_REG0+11), "4*REG_REG11" },
2790 { 4*(REG_REG0+12), "4*REG_REG12" },
2791 { 4*(REG_REG0+13), "4*REG_REG13" },
2792 { 4*(REG_REG0+14), "4*REG_REG14" },
2793 { 4*REG_REG15, "4*REG_REG15" },
2794 { 4*REG_PC, "4*REG_PC" },
2795 { 4*REG_PR, "4*REG_PR" },
2796 { 4*REG_SR, "4*REG_SR" },
2797 { 4*REG_GBR, "4*REG_GBR" },
2798 { 4*REG_MACH, "4*REG_MACH" },
2799 { 4*REG_MACL, "4*REG_MACL" },
2800 { 4*REG_SYSCALL, "4*REG_SYSCALL" },
2801 { 4*REG_FPUL, "4*REG_FPUL" },
2802 { 4*REG_FPREG0, "4*REG_FPREG0" },
2803 { 4*(REG_FPREG0+1), "4*REG_FPREG1" },
2804 { 4*(REG_FPREG0+2), "4*REG_FPREG2" },
2805 { 4*(REG_FPREG0+3), "4*REG_FPREG3" },
2806 { 4*(REG_FPREG0+4), "4*REG_FPREG4" },
2807 { 4*(REG_FPREG0+5), "4*REG_FPREG5" },
2808 { 4*(REG_FPREG0+6), "4*REG_FPREG6" },
2809 { 4*(REG_FPREG0+7), "4*REG_FPREG7" },
2810 { 4*(REG_FPREG0+8), "4*REG_FPREG8" },
2811 { 4*(REG_FPREG0+9), "4*REG_FPREG9" },
2812 { 4*(REG_FPREG0+10), "4*REG_FPREG10" },
2813 { 4*(REG_FPREG0+11), "4*REG_FPREG11" },
2814 { 4*(REG_FPREG0+12), "4*REG_FPREG12" },
2815 { 4*(REG_FPREG0+13), "4*REG_FPREG13" },
2816 { 4*(REG_FPREG0+14), "4*REG_FPREG14" },
2817 { 4*REG_FPREG15, "4*REG_FPREG15" },
Roland McGrathc0f8bbd2003-08-21 09:58:00 +00002818#ifdef REG_XDREG0
Denys Vlasenkoadedb512008-12-30 18:47:55 +00002819 { 4*REG_XDREG0, "4*REG_XDREG0" },
2820 { 4*(REG_XDREG0+2), "4*REG_XDREG2" },
2821 { 4*(REG_XDREG0+4), "4*REG_XDREG4" },
2822 { 4*(REG_XDREG0+6), "4*REG_XDREG6" },
2823 { 4*(REG_XDREG0+8), "4*REG_XDREG8" },
2824 { 4*(REG_XDREG0+10), "4*REG_XDREG10" },
2825 { 4*(REG_XDREG0+12), "4*REG_XDREG12" },
2826 { 4*REG_XDREG14, "4*REG_XDREG14" },
Roland McGrathc0f8bbd2003-08-21 09:58:00 +00002827#endif
Denys Vlasenkoadedb512008-12-30 18:47:55 +00002828 { 4*REG_FPSCR, "4*REG_FPSCR" },
Wichert Akkermanccef6372002-05-01 16:39:22 +00002829#endif /* SH */
Roland McGrathf5a47772003-06-26 22:40:42 +00002830#ifdef SH64
Roland McGrathe1e584b2003-06-02 19:18:58 +00002831 { 0, "PC(L)" },
2832 { 4, "PC(U)" },
2833 { 8, "SR(L)" },
2834 { 12, "SR(U)" },
2835 { 16, "syscall no.(L)" },
2836 { 20, "syscall_no.(U)" },
2837 { 24, "R0(L)" },
2838 { 28, "R0(U)" },
2839 { 32, "R1(L)" },
2840 { 36, "R1(U)" },
2841 { 40, "R2(L)" },
2842 { 44, "R2(U)" },
2843 { 48, "R3(L)" },
2844 { 52, "R3(U)" },
2845 { 56, "R4(L)" },
2846 { 60, "R4(U)" },
2847 { 64, "R5(L)" },
2848 { 68, "R5(U)" },
2849 { 72, "R6(L)" },
2850 { 76, "R6(U)" },
2851 { 80, "R7(L)" },
2852 { 84, "R7(U)" },
2853 { 88, "R8(L)" },
2854 { 92, "R8(U)" },
2855 { 96, "R9(L)" },
2856 { 100, "R9(U)" },
2857 { 104, "R10(L)" },
2858 { 108, "R10(U)" },
2859 { 112, "R11(L)" },
2860 { 116, "R11(U)" },
2861 { 120, "R12(L)" },
2862 { 124, "R12(U)" },
2863 { 128, "R13(L)" },
2864 { 132, "R13(U)" },
2865 { 136, "R14(L)" },
2866 { 140, "R14(U)" },
2867 { 144, "R15(L)" },
2868 { 148, "R15(U)" },
2869 { 152, "R16(L)" },
2870 { 156, "R16(U)" },
2871 { 160, "R17(L)" },
2872 { 164, "R17(U)" },
2873 { 168, "R18(L)" },
2874 { 172, "R18(U)" },
2875 { 176, "R19(L)" },
2876 { 180, "R19(U)" },
2877 { 184, "R20(L)" },
2878 { 188, "R20(U)" },
2879 { 192, "R21(L)" },
2880 { 196, "R21(U)" },
2881 { 200, "R22(L)" },
2882 { 204, "R22(U)" },
2883 { 208, "R23(L)" },
2884 { 212, "R23(U)" },
2885 { 216, "R24(L)" },
2886 { 220, "R24(U)" },
2887 { 224, "R25(L)" },
2888 { 228, "R25(U)" },
2889 { 232, "R26(L)" },
2890 { 236, "R26(U)" },
2891 { 240, "R27(L)" },
2892 { 244, "R27(U)" },
2893 { 248, "R28(L)" },
2894 { 252, "R28(U)" },
2895 { 256, "R29(L)" },
2896 { 260, "R29(U)" },
2897 { 264, "R30(L)" },
2898 { 268, "R30(U)" },
2899 { 272, "R31(L)" },
2900 { 276, "R31(U)" },
2901 { 280, "R32(L)" },
2902 { 284, "R32(U)" },
2903 { 288, "R33(L)" },
2904 { 292, "R33(U)" },
2905 { 296, "R34(L)" },
2906 { 300, "R34(U)" },
2907 { 304, "R35(L)" },
2908 { 308, "R35(U)" },
2909 { 312, "R36(L)" },
2910 { 316, "R36(U)" },
2911 { 320, "R37(L)" },
2912 { 324, "R37(U)" },
2913 { 328, "R38(L)" },
2914 { 332, "R38(U)" },
2915 { 336, "R39(L)" },
2916 { 340, "R39(U)" },
2917 { 344, "R40(L)" },
2918 { 348, "R40(U)" },
2919 { 352, "R41(L)" },
2920 { 356, "R41(U)" },
2921 { 360, "R42(L)" },
2922 { 364, "R42(U)" },
2923 { 368, "R43(L)" },
2924 { 372, "R43(U)" },
2925 { 376, "R44(L)" },
2926 { 380, "R44(U)" },
2927 { 384, "R45(L)" },
2928 { 388, "R45(U)" },
2929 { 392, "R46(L)" },
2930 { 396, "R46(U)" },
2931 { 400, "R47(L)" },
2932 { 404, "R47(U)" },
2933 { 408, "R48(L)" },
2934 { 412, "R48(U)" },
2935 { 416, "R49(L)" },
2936 { 420, "R49(U)" },
2937 { 424, "R50(L)" },
2938 { 428, "R50(U)" },
2939 { 432, "R51(L)" },
2940 { 436, "R51(U)" },
2941 { 440, "R52(L)" },
2942 { 444, "R52(U)" },
2943 { 448, "R53(L)" },
2944 { 452, "R53(U)" },
2945 { 456, "R54(L)" },
2946 { 460, "R54(U)" },
2947 { 464, "R55(L)" },
2948 { 468, "R55(U)" },
2949 { 472, "R56(L)" },
2950 { 476, "R56(U)" },
2951 { 480, "R57(L)" },
2952 { 484, "R57(U)" },
2953 { 488, "R58(L)" },
2954 { 492, "R58(U)" },
2955 { 496, "R59(L)" },
2956 { 500, "R59(U)" },
2957 { 504, "R60(L)" },
2958 { 508, "R60(U)" },
2959 { 512, "R61(L)" },
2960 { 516, "R61(U)" },
2961 { 520, "R62(L)" },
2962 { 524, "R62(U)" },
2963 { 528, "TR0(L)" },
2964 { 532, "TR0(U)" },
2965 { 536, "TR1(L)" },
2966 { 540, "TR1(U)" },
2967 { 544, "TR2(L)" },
2968 { 548, "TR2(U)" },
2969 { 552, "TR3(L)" },
2970 { 556, "TR3(U)" },
2971 { 560, "TR4(L)" },
2972 { 564, "TR4(U)" },
2973 { 568, "TR5(L)" },
2974 { 572, "TR5(U)" },
2975 { 576, "TR6(L)" },
2976 { 580, "TR6(U)" },
2977 { 584, "TR7(L)" },
2978 { 588, "TR7(U)" },
Denys Vlasenkoadedb512008-12-30 18:47:55 +00002979 /* This entry is in case pt_regs contains dregs (depends on
2980 the kernel build options). */
Roland McGrathe1e584b2003-06-02 19:18:58 +00002981 { uoff(regs), "offsetof(struct user, regs)" },
2982 { uoff(fpu), "offsetof(struct user, fpu)" },
2983#endif
Roland McGrath0f87c492003-06-03 23:29:04 +00002984#ifdef ARM
2985 { uoff(regs.ARM_r0), "r0" },
2986 { uoff(regs.ARM_r1), "r1" },
2987 { uoff(regs.ARM_r2), "r2" },
2988 { uoff(regs.ARM_r3), "r3" },
2989 { uoff(regs.ARM_r4), "r4" },
2990 { uoff(regs.ARM_r5), "r5" },
2991 { uoff(regs.ARM_r6), "r6" },
2992 { uoff(regs.ARM_r7), "r7" },
2993 { uoff(regs.ARM_r8), "r8" },
2994 { uoff(regs.ARM_r9), "r9" },
2995 { uoff(regs.ARM_r10), "r10" },
2996 { uoff(regs.ARM_fp), "fp" },
2997 { uoff(regs.ARM_ip), "ip" },
2998 { uoff(regs.ARM_sp), "sp" },
2999 { uoff(regs.ARM_lr), "lr" },
3000 { uoff(regs.ARM_pc), "pc" },
3001 { uoff(regs.ARM_cpsr), "cpsr" },
3002#endif
Wichert Akkermanccef6372002-05-01 16:39:22 +00003003
Roland McGrath542c2c62008-05-20 01:11:56 +00003004#ifdef MIPS
3005 { 0, "r0" },
3006 { 1, "r1" },
3007 { 2, "r2" },
3008 { 3, "r3" },
3009 { 4, "r4" },
3010 { 5, "r5" },
3011 { 6, "r6" },
3012 { 7, "r7" },
3013 { 8, "r8" },
3014 { 9, "r9" },
3015 { 10, "r10" },
3016 { 11, "r11" },
3017 { 12, "r12" },
3018 { 13, "r13" },
3019 { 14, "r14" },
3020 { 15, "r15" },
3021 { 16, "r16" },
3022 { 17, "r17" },
3023 { 18, "r18" },
3024 { 19, "r19" },
3025 { 20, "r20" },
3026 { 21, "r21" },
3027 { 22, "r22" },
3028 { 23, "r23" },
3029 { 24, "r24" },
3030 { 25, "r25" },
3031 { 26, "r26" },
3032 { 27, "r27" },
3033 { 28, "r28" },
3034 { 29, "r29" },
3035 { 30, "r30" },
3036 { 31, "r31" },
3037 { 32, "f0" },
3038 { 33, "f1" },
3039 { 34, "f2" },
3040 { 35, "f3" },
3041 { 36, "f4" },
3042 { 37, "f5" },
3043 { 38, "f6" },
3044 { 39, "f7" },
3045 { 40, "f8" },
3046 { 41, "f9" },
3047 { 42, "f10" },
3048 { 43, "f11" },
3049 { 44, "f12" },
3050 { 45, "f13" },
3051 { 46, "f14" },
3052 { 47, "f15" },
3053 { 48, "f16" },
3054 { 49, "f17" },
3055 { 50, "f18" },
3056 { 51, "f19" },
3057 { 52, "f20" },
3058 { 53, "f21" },
3059 { 54, "f22" },
3060 { 55, "f23" },
3061 { 56, "f24" },
3062 { 57, "f25" },
3063 { 58, "f26" },
3064 { 59, "f27" },
3065 { 60, "f28" },
3066 { 61, "f29" },
3067 { 62, "f30" },
3068 { 63, "f31" },
3069 { 64, "pc" },
3070 { 65, "cause" },
3071 { 66, "badvaddr" },
3072 { 67, "mmhi" },
3073 { 68, "mmlo" },
3074 { 69, "fpcsr" },
3075 { 70, "fpeir" },
3076#endif
3077
Dmitry V. Levin87ea1f42008-11-10 22:21:41 +00003078#if !defined(S390) && !defined(S390X) && !defined(MIPS) && !defined(SPARC64) && !defined(BFIN)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003079 { uoff(u_fpvalid), "offsetof(struct user, u_fpvalid)" },
Wichert Akkermanf90da011999-10-31 21:15:38 +00003080#endif
Michal Ludvig0e035502002-09-23 15:41:01 +00003081#if defined(I386) || defined(X86_64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003082 { uoff(i387), "offsetof(struct user, i387)" },
3083#else /* !I386 */
3084#ifdef M68K
3085 { uoff(m68kfp), "offsetof(struct user, m68kfp)" },
3086#endif /* M68K */
3087#endif /* !I386 */
3088 { uoff(u_tsize), "offsetof(struct user, u_tsize)" },
3089 { uoff(u_dsize), "offsetof(struct user, u_dsize)" },
3090 { uoff(u_ssize), "offsetof(struct user, u_ssize)" },
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003091#if !defined(SPARC64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003092 { uoff(start_code), "offsetof(struct user, start_code)" },
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003093#endif
Roland McGrathf5a47772003-06-26 22:40:42 +00003094#ifdef SH64
Roland McGrathe1e584b2003-06-02 19:18:58 +00003095 { uoff(start_data), "offsetof(struct user, start_data)" },
3096#endif
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003097#if !defined(SPARC64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003098 { uoff(start_stack), "offsetof(struct user, start_stack)" },
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003099#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003100 { uoff(signal), "offsetof(struct user, signal)" },
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003101#if !defined(S390) && !defined(S390X) && !defined(MIPS) && !defined(SH) && !defined(SH64) && !defined(SPARC64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003102 { uoff(reserved), "offsetof(struct user, reserved)" },
Wichert Akkermanf90da011999-10-31 21:15:38 +00003103#endif
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003104#if !defined(SPARC64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003105 { uoff(u_ar0), "offsetof(struct user, u_ar0)" },
Roland McGrath6d1a65c2004-07-12 07:44:08 +00003106#endif
Dmitry V. Levin87ea1f42008-11-10 22:21:41 +00003107#if !defined(ARM) && !defined(MIPS) && !defined(S390) && !defined(S390X) && !defined(SPARC64) && !defined(BFIN)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003108 { uoff(u_fpstate), "offsetof(struct user, u_fpstate)" },
3109#endif
3110 { uoff(magic), "offsetof(struct user, magic)" },
3111 { uoff(u_comm), "offsetof(struct user, u_comm)" },
Michal Ludvig0e035502002-09-23 15:41:01 +00003112#if defined(I386) || defined(X86_64)
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003113 { uoff(u_debugreg), "offsetof(struct user, u_debugreg)" },
3114#endif /* I386 */
Wichert Akkerman8b1b40c2000-02-03 21:58:30 +00003115#endif /* !IA64 */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003116#endif /* !ALPHA */
3117#endif /* !POWERPC/!SPARC */
3118#endif /* LINUX */
3119#ifdef SUNOS4
3120 { uoff(u_pcb), "offsetof(struct user, u_pcb)" },
3121 { uoff(u_procp), "offsetof(struct user, u_procp)" },
3122 { uoff(u_ar0), "offsetof(struct user, u_ar0)" },
3123 { uoff(u_comm[0]), "offsetof(struct user, u_comm[0])" },
3124 { uoff(u_arg[0]), "offsetof(struct user, u_arg[0])" },
3125 { uoff(u_ap), "offsetof(struct user, u_ap)" },
3126 { uoff(u_qsave), "offsetof(struct user, u_qsave)" },
3127 { uoff(u_rval1), "offsetof(struct user, u_rval1)" },
3128 { uoff(u_rval2), "offsetof(struct user, u_rval2)" },
3129 { uoff(u_error), "offsetof(struct user, u_error)" },
3130 { uoff(u_eosys), "offsetof(struct user, u_eosys)" },
3131 { uoff(u_ssave), "offsetof(struct user, u_ssave)" },
3132 { uoff(u_signal[0]), "offsetof(struct user, u_signal)" },
3133 { uoff(u_sigmask[0]), "offsetof(struct user, u_sigmask)" },
3134 { uoff(u_sigonstack), "offsetof(struct user, u_sigonstack)" },
3135 { uoff(u_sigintr), "offsetof(struct user, u_sigintr)" },
3136 { uoff(u_sigreset), "offsetof(struct user, u_sigreset)" },
3137 { uoff(u_oldmask), "offsetof(struct user, u_oldmask)" },
3138 { uoff(u_code), "offsetof(struct user, u_code)" },
3139 { uoff(u_addr), "offsetof(struct user, u_addr)" },
3140 { uoff(u_sigstack), "offsetof(struct user, u_sigstack)" },
3141 { uoff(u_ofile), "offsetof(struct user, u_ofile)" },
3142 { uoff(u_pofile), "offsetof(struct user, u_pofile)" },
3143 { uoff(u_ofile_arr[0]), "offsetof(struct user, u_ofile_arr[0])" },
3144 { uoff(u_pofile_arr[0]),"offsetof(struct user, u_pofile_arr[0])"},
3145 { uoff(u_lastfile), "offsetof(struct user, u_lastfile)" },
3146 { uoff(u_cwd), "offsetof(struct user, u_cwd)" },
3147 { uoff(u_cdir), "offsetof(struct user, u_cdir)" },
3148 { uoff(u_rdir), "offsetof(struct user, u_rdir)" },
3149 { uoff(u_cmask), "offsetof(struct user, u_cmask)" },
3150 { uoff(u_ru), "offsetof(struct user, u_ru)" },
3151 { uoff(u_cru), "offsetof(struct user, u_cru)" },
3152 { uoff(u_timer[0]), "offsetof(struct user, u_timer[0])" },
3153 { uoff(u_XXX[0]), "offsetof(struct user, u_XXX[0])" },
3154 { uoff(u_ioch), "offsetof(struct user, u_ioch)" },
3155 { uoff(u_start), "offsetof(struct user, u_start)" },
3156 { uoff(u_acflag), "offsetof(struct user, u_acflag)" },
3157 { uoff(u_prof.pr_base), "offsetof(struct user, u_prof.pr_base)" },
3158 { uoff(u_prof.pr_size), "offsetof(struct user, u_prof.pr_size)" },
3159 { uoff(u_prof.pr_off), "offsetof(struct user, u_prof.pr_off)" },
3160 { uoff(u_prof.pr_scale),"offsetof(struct user, u_prof.pr_scale)"},
3161 { uoff(u_rlimit[0]), "offsetof(struct user, u_rlimit)" },
3162 { uoff(u_exdata.Ux_A), "offsetof(struct user, u_exdata.Ux_A)" },
3163 { uoff(u_exdata.ux_shell[0]),"offsetof(struct user, u_exdata.ux_shell[0])"},
3164 { uoff(u_lofault), "offsetof(struct user, u_lofault)" },
3165#endif /* SUNOS4 */
Wichert Akkermanc1652e22001-03-27 12:17:16 +00003166#ifndef HPPA
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003167 { sizeof(struct user), "sizeof(struct user)" },
Wichert Akkermanc1652e22001-03-27 12:17:16 +00003168#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003169 { 0, NULL },
3170};
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00003171#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003172
3173int
3174sys_ptrace(tcp)
3175struct tcb *tcp;
3176{
Roland McGrathd9f816f2004-09-04 03:39:20 +00003177 const struct xlat *x;
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003178 long addr;
3179
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003180 if (entering(tcp)) {
Roland McGrathbf621d42003-01-14 09:46:21 +00003181 printxval(ptrace_cmds, tcp->u_arg[0],
3182#ifndef FREEBSD
3183 "PTRACE_???"
3184#else
3185 "PT_???"
3186#endif
3187 );
3188 tprintf(", %lu, ", tcp->u_arg[1]);
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003189 addr = tcp->u_arg[2];
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00003190#ifndef FREEBSD
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003191 if (tcp->u_arg[0] == PTRACE_PEEKUSER
3192 || tcp->u_arg[0] == PTRACE_POKEUSER) {
3193 for (x = struct_user_offsets; x->str; x++) {
3194 if (x->val >= addr)
3195 break;
3196 }
3197 if (!x->str)
3198 tprintf("%#lx, ", addr);
3199 else if (x->val > addr && x != struct_user_offsets) {
3200 x--;
3201 tprintf("%s + %ld, ", x->str, addr - x->val);
3202 }
3203 else
3204 tprintf("%s, ", x->str);
3205 }
3206 else
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00003207#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003208 tprintf("%#lx, ", tcp->u_arg[2]);
3209#ifdef LINUX
3210 switch (tcp->u_arg[0]) {
Roland McGrath1e868062007-11-19 22:11:45 +00003211#ifndef IA64
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003212 case PTRACE_PEEKDATA:
3213 case PTRACE_PEEKTEXT:
3214 case PTRACE_PEEKUSER:
3215 break;
Roland McGrath1e868062007-11-19 22:11:45 +00003216#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003217 case PTRACE_CONT:
3218 case PTRACE_SINGLESTEP:
3219 case PTRACE_SYSCALL:
3220 case PTRACE_DETACH:
3221 printsignal(tcp->u_arg[3]);
3222 break;
Denys Vlasenkof535b542009-01-13 18:30:55 +00003223#ifdef PTRACE_SETOPTIONS
3224 case PTRACE_SETOPTIONS:
3225 printflags(ptrace_setoptions_flags, tcp->u_arg[3], "PTRACE_O_???");
3226 break;
3227#endif
3228#ifdef PTRACE_SETSIGINFO
3229 case PTRACE_SETSIGINFO: {
3230 siginfo_t si;
3231 if (!tcp->u_arg[3])
3232 tprintf("NULL");
3233 else if (syserror(tcp))
3234 tprintf("%#lx", tcp->u_arg[3]);
3235 else if (umove(tcp, tcp->u_arg[3], &si) < 0)
3236 tprintf("{???}");
3237 else
3238 printsiginfo(&si, verbose(tcp));
3239 break;
3240 }
3241#endif
3242#ifdef PTRACE_GETSIGINFO
3243 case PTRACE_GETSIGINFO:
3244 /* Don't print anything, do it at syscall return. */
3245 break;
3246#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003247 default:
3248 tprintf("%#lx", tcp->u_arg[3]);
3249 break;
3250 }
3251 } else {
3252 switch (tcp->u_arg[0]) {
3253 case PTRACE_PEEKDATA:
3254 case PTRACE_PEEKTEXT:
3255 case PTRACE_PEEKUSER:
Roland McGrath1e868062007-11-19 22:11:45 +00003256#ifdef IA64
3257 return RVAL_HEX;
3258#else
Roland McGratheb285352003-01-14 09:59:00 +00003259 printnum(tcp, tcp->u_arg[3], "%#lx");
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003260 break;
Roland McGrath1e868062007-11-19 22:11:45 +00003261#endif
Denys Vlasenkof535b542009-01-13 18:30:55 +00003262#ifdef PTRACE_GETSIGINFO
3263 case PTRACE_GETSIGINFO: {
3264 siginfo_t si;
3265 if (!tcp->u_arg[3])
3266 tprintf("NULL");
3267 else if (syserror(tcp))
3268 tprintf("%#lx", tcp->u_arg[3]);
3269 else if (umove(tcp, tcp->u_arg[3], &si) < 0)
3270 tprintf("{???}");
3271 else
3272 printsiginfo(&si, verbose(tcp));
3273 break;
3274 }
3275#endif
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003276 }
3277 }
3278#endif /* LINUX */
3279#ifdef SUNOS4
3280 if (tcp->u_arg[0] == PTRACE_WRITEDATA ||
3281 tcp->u_arg[0] == PTRACE_WRITETEXT) {
3282 tprintf("%lu, ", tcp->u_arg[3]);
3283 printstr(tcp, tcp->u_arg[4], tcp->u_arg[3]);
3284 } else if (tcp->u_arg[0] != PTRACE_READDATA &&
3285 tcp->u_arg[0] != PTRACE_READTEXT) {
3286 tprintf("%#lx", tcp->u_arg[3]);
3287 }
3288 } else {
3289 if (tcp->u_arg[0] == PTRACE_READDATA ||
3290 tcp->u_arg[0] == PTRACE_READTEXT) {
3291 tprintf("%lu, ", tcp->u_arg[3]);
3292 printstr(tcp, tcp->u_arg[4], tcp->u_arg[3]);
3293 }
3294 }
3295#endif /* SUNOS4 */
Wichert Akkermanbf79f2e2000-09-01 21:03:06 +00003296#ifdef FREEBSD
3297 tprintf("%lu", tcp->u_arg[3]);
3298 }
3299#endif /* FREEBSD */
Wichert Akkerman76baf7c1999-02-19 00:21:36 +00003300 return 0;
3301}
3302
3303#endif /* !SVR4 */
Roland McGrath5a223472002-12-15 23:58:26 +00003304
3305#ifdef LINUX
Roland McGrath51942a92007-07-05 18:59:11 +00003306# ifndef FUTEX_CMP_REQUEUE
3307# define FUTEX_CMP_REQUEUE 4
3308# endif
3309# ifndef FUTEX_WAKE_OP
3310# define FUTEX_WAKE_OP 5
3311# endif
3312# ifndef FUTEX_LOCK_PI
3313# define FUTEX_LOCK_PI 6
3314# define FUTEX_UNLOCK_PI 7
3315# define FUTEX_TRYLOCK_PI 8
3316# endif
Roland McGrath1aeaf742008-07-18 01:27:39 +00003317# ifndef FUTEX_WAIT_BITSET
3318# define FUTEX_WAIT_BITSET 9
3319# endif
3320# ifndef FUTEX_WAKE_BITSET
3321# define FUTEX_WAKE_BITSET 10
Roland McGrath51942a92007-07-05 18:59:11 +00003322# endif
3323# ifndef FUTEX_PRIVATE_FLAG
3324# define FUTEX_PRIVATE_FLAG 128
3325# endif
Roland McGrathd9f816f2004-09-04 03:39:20 +00003326static const struct xlat futexops[] = {
Roland McGrath51942a92007-07-05 18:59:11 +00003327 { FUTEX_WAIT, "FUTEX_WAIT" },
3328 { FUTEX_WAKE, "FUTEX_WAKE" },
3329 { FUTEX_FD, "FUTEX_FD" },
3330 { FUTEX_REQUEUE, "FUTEX_REQUEUE" },
3331 { FUTEX_CMP_REQUEUE, "FUTEX_CMP_REQUEUE" },
3332 { FUTEX_WAKE_OP, "FUTEX_WAKE_OP" },
3333 { FUTEX_LOCK_PI, "FUTEX_LOCK_PI" },
3334 { FUTEX_UNLOCK_PI, "FUTEX_UNLOCK_PI" },
3335 { FUTEX_TRYLOCK_PI, "FUTEX_TRYLOCK_PI" },
Roland McGrath1aeaf742008-07-18 01:27:39 +00003336 { FUTEX_WAIT_BITSET, "FUTEX_WAIT_BITSET" },
3337 { FUTEX_WAKE_BITSET, "FUTEX_WAKE_BITSET" },
Roland McGrath51942a92007-07-05 18:59:11 +00003338 { FUTEX_WAIT|FUTEX_PRIVATE_FLAG, "FUTEX_WAIT_PRIVATE" },
3339 { FUTEX_WAKE|FUTEX_PRIVATE_FLAG, "FUTEX_WAKE_PRIVATE" },
3340 { FUTEX_FD|FUTEX_PRIVATE_FLAG, "FUTEX_FD_PRIVATE" },
3341 { FUTEX_REQUEUE|FUTEX_PRIVATE_FLAG, "FUTEX_REQUEUE_PRIVATE" },
3342 { FUTEX_CMP_REQUEUE|FUTEX_PRIVATE_FLAG, "FUTEX_CMP_REQUEUE_PRIVATE" },
3343 { FUTEX_WAKE_OP|FUTEX_PRIVATE_FLAG, "FUTEX_WAKE_OP_PRIVATE" },
3344 { FUTEX_LOCK_PI|FUTEX_PRIVATE_FLAG, "FUTEX_LOCK_PI_PRIVATE" },
3345 { FUTEX_UNLOCK_PI|FUTEX_PRIVATE_FLAG, "FUTEX_UNLOCK_PI_PRIVATE" },
3346 { FUTEX_TRYLOCK_PI|FUTEX_PRIVATE_FLAG, "FUTEX_TRYLOCK_PI_PRIVATE" },
Roland McGrath1aeaf742008-07-18 01:27:39 +00003347 { FUTEX_WAIT_BITSET|FUTEX_PRIVATE_FLAG, "FUTEX_WAIT_BITSET_PRIVATE" },
3348 { FUTEX_WAKE_BITSET|FUTEX_PRIVATE_FLAG, "FUTEX_WAKE_BITSET_PRIVATE" },
Roland McGrath51942a92007-07-05 18:59:11 +00003349 { 0, NULL }
3350};
3351#ifndef FUTEX_OP_SET
3352# define FUTEX_OP_SET 0
3353# define FUTEX_OP_ADD 1
3354# define FUTEX_OP_OR 2
3355# define FUTEX_OP_ANDN 3
3356# define FUTEX_OP_XOR 4
3357# define FUTEX_OP_CMP_EQ 0
3358# define FUTEX_OP_CMP_NE 1
3359# define FUTEX_OP_CMP_LT 2
3360# define FUTEX_OP_CMP_LE 3
3361# define FUTEX_OP_CMP_GT 4
3362# define FUTEX_OP_CMP_GE 5
3363#endif
3364static const struct xlat futexwakeops[] = {
3365 { FUTEX_OP_SET, "FUTEX_OP_SET" },
3366 { FUTEX_OP_ADD, "FUTEX_OP_ADD" },
3367 { FUTEX_OP_OR, "FUTEX_OP_OR" },
3368 { FUTEX_OP_ANDN, "FUTEX_OP_ANDN" },
3369 { FUTEX_OP_XOR, "FUTEX_OP_XOR" },
3370 { 0, NULL }
3371};
3372static const struct xlat futexwakecmps[] = {
3373 { FUTEX_OP_CMP_EQ, "FUTEX_OP_CMP_EQ" },
3374 { FUTEX_OP_CMP_NE, "FUTEX_OP_CMP_NE" },
3375 { FUTEX_OP_CMP_LT, "FUTEX_OP_CMP_LT" },
3376 { FUTEX_OP_CMP_LE, "FUTEX_OP_CMP_LE" },
3377 { FUTEX_OP_CMP_GT, "FUTEX_OP_CMP_GT" },
3378 { FUTEX_OP_CMP_GE, "FUTEX_OP_CMP_GE" },
3379 { 0, NULL }
Roland McGrath5a223472002-12-15 23:58:26 +00003380};
3381
3382int
3383sys_futex(tcp)
3384struct tcb *tcp;
3385{
3386 if (entering(tcp)) {
Roland McGrath1aeaf742008-07-18 01:27:39 +00003387 long int cmd = tcp->u_arg[1] & 127;
Roland McGrath5a223472002-12-15 23:58:26 +00003388 tprintf("%p, ", (void *) tcp->u_arg[0]);
Roland McGrath88812d62003-06-26 22:27:23 +00003389 printxval(futexops, tcp->u_arg[1], "FUTEX_???");
Roland McGrath8dfa04a2003-03-05 04:07:55 +00003390 tprintf(", %ld", tcp->u_arg[2]);
Roland McGrath1aeaf742008-07-18 01:27:39 +00003391 if (cmd == FUTEX_WAKE_BITSET)
3392 tprintf(", %lx", tcp->u_arg[5]);
3393 else if (cmd == FUTEX_WAIT) {
Roland McGrath8dfa04a2003-03-05 04:07:55 +00003394 tprintf(", ");
3395 printtv(tcp, tcp->u_arg[3]);
Roland McGrath1aeaf742008-07-18 01:27:39 +00003396 } else if (cmd == FUTEX_WAIT_BITSET) {
3397 tprintf(", ");
3398 printtv(tcp, tcp->u_arg[3]);
3399 tprintf(", %lx", tcp->u_arg[5]);
Roland McGrath51942a92007-07-05 18:59:11 +00003400 } else if (cmd == FUTEX_REQUEUE)
Roland McGrath88812d62003-06-26 22:27:23 +00003401 tprintf(", %ld, %p", tcp->u_arg[3], (void *) tcp->u_arg[4]);
Roland McGrath51942a92007-07-05 18:59:11 +00003402 else if (cmd == FUTEX_CMP_REQUEUE)
3403 tprintf(", %ld, %p, %ld", tcp->u_arg[3], (void *) tcp->u_arg[4], tcp->u_arg[5]);
3404 else if (cmd == FUTEX_WAKE_OP) {
3405 tprintf(", %ld, %p, {", tcp->u_arg[3], (void *) tcp->u_arg[4]);
3406 if ((tcp->u_arg[5] >> 28) & 8)
3407 tprintf("FUTEX_OP_OPARG_SHIFT|");
3408 printxval(futexwakeops, (tcp->u_arg[5] >> 28) & 0x7, "FUTEX_OP_???");
3409 tprintf(", %ld, ", (tcp->u_arg[5] >> 12) & 0xfff);
3410 if ((tcp->u_arg[5] >> 24) & 8)
3411 tprintf("FUTEX_OP_OPARG_SHIFT|");
3412 printxval(futexwakecmps, (tcp->u_arg[5] >> 24) & 0x7, "FUTEX_OP_CMP_???");
3413 tprintf(", %ld}", tcp->u_arg[5] & 0xfff);
3414 }
Roland McGrath5a223472002-12-15 23:58:26 +00003415 }
3416 return 0;
3417}
3418
3419static void
Roland McGrath79fbda52004-04-14 02:45:55 +00003420print_affinitylist(tcp, list, len)
3421struct tcb *tcp;
3422long list;
Roland McGrath5a223472002-12-15 23:58:26 +00003423unsigned int len;
3424{
3425 int first = 1;
3426 tprintf(" {");
Roland McGratha2f34962003-05-23 00:14:04 +00003427 while (len >= sizeof (unsigned long)) {
Roland McGrath79fbda52004-04-14 02:45:55 +00003428 unsigned long w;
3429 umove(tcp, list, &w);
3430 tprintf("%s %lx", first ? "" : ",", w);
Roland McGrath5a223472002-12-15 23:58:26 +00003431 first = 0;
3432 len -= sizeof (unsigned long);
Roland McGrath79fbda52004-04-14 02:45:55 +00003433 list += sizeof(unsigned long);
Roland McGrath5a223472002-12-15 23:58:26 +00003434 }
3435 tprintf(" }");
3436}
3437
3438int
3439sys_sched_setaffinity(tcp)
3440struct tcb *tcp;
3441{
3442 if (entering(tcp)) {
3443 tprintf("%ld, %lu, ", tcp->u_arg[0], tcp->u_arg[1]);
Roland McGrath79fbda52004-04-14 02:45:55 +00003444 print_affinitylist(tcp, tcp->u_arg[2], tcp->u_arg[1]);
Roland McGrath5a223472002-12-15 23:58:26 +00003445 }
3446 return 0;
3447}
3448
3449int
3450sys_sched_getaffinity(tcp)
3451struct tcb *tcp;
3452{
3453 if (entering(tcp)) {
3454 tprintf("%ld, %lu, ", tcp->u_arg[0], tcp->u_arg[1]);
3455 } else {
Roland McGrath79fbda52004-04-14 02:45:55 +00003456 if (tcp->u_rval == -1)
3457 tprintf("%#lx", tcp->u_arg[2]);
3458 else
3459 print_affinitylist(tcp, tcp->u_arg[2], tcp->u_rval);
Roland McGrath5a223472002-12-15 23:58:26 +00003460 }
3461 return 0;
3462}
Roland McGrath279d3782004-03-01 20:27:37 +00003463
Roland McGrathd9f816f2004-09-04 03:39:20 +00003464static const struct xlat schedulers[] = {
Roland McGrath279d3782004-03-01 20:27:37 +00003465 { SCHED_OTHER, "SCHED_OTHER" },
3466 { SCHED_RR, "SCHED_RR" },
3467 { SCHED_FIFO, "SCHED_FIFO" },
3468 { 0, NULL }
3469};
3470
3471int
3472sys_sched_getscheduler(tcp)
3473struct tcb *tcp;
3474{
3475 if (entering(tcp)) {
3476 tprintf("%d", (int) tcp->u_arg[0]);
3477 } else if (! syserror(tcp)) {
3478 tcp->auxstr = xlookup (schedulers, tcp->u_rval);
3479 if (tcp->auxstr != NULL)
3480 return RVAL_STR;
3481 }
3482 return 0;
3483}
3484
3485int
3486sys_sched_setscheduler(tcp)
3487struct tcb *tcp;
3488{
3489 if (entering(tcp)) {
3490 struct sched_param p;
3491 tprintf("%d, ", (int) tcp->u_arg[0]);
3492 printxval(schedulers, tcp->u_arg[1], "SCHED_???");
3493 if (umove(tcp, tcp->u_arg[2], &p) < 0)
Roland McGrathc2d5eb02005-02-02 04:16:56 +00003494 tprintf(", %#lx", tcp->u_arg[2]);
Roland McGrath279d3782004-03-01 20:27:37 +00003495 else
3496 tprintf(", { %d }", p.__sched_priority);
3497 }
3498 return 0;
3499}
3500
3501int
3502sys_sched_getparam(tcp)
3503struct tcb *tcp;
3504{
3505 if (entering(tcp)) {
3506 tprintf("%d, ", (int) tcp->u_arg[0]);
3507 } else {
3508 struct sched_param p;
3509 if (umove(tcp, tcp->u_arg[1], &p) < 0)
Roland McGrathc2d5eb02005-02-02 04:16:56 +00003510 tprintf("%#lx", tcp->u_arg[1]);
Roland McGrath279d3782004-03-01 20:27:37 +00003511 else
3512 tprintf("{ %d }", p.__sched_priority);
3513 }
3514 return 0;
3515}
3516
3517int
3518sys_sched_setparam(tcp)
3519struct tcb *tcp;
3520{
3521 if (entering(tcp)) {
3522 struct sched_param p;
3523 if (umove(tcp, tcp->u_arg[1], &p) < 0)
Roland McGrathc2d5eb02005-02-02 04:16:56 +00003524 tprintf("%d, %#lx", (int) tcp->u_arg[0], tcp->u_arg[1]);
Roland McGrath279d3782004-03-01 20:27:37 +00003525 else
3526 tprintf("%d, { %d }", (int) tcp->u_arg[0], p.__sched_priority);
3527 }
3528 return 0;
3529}
3530
3531int
3532sys_sched_get_priority_min(tcp)
3533struct tcb *tcp;
3534{
3535 if (entering(tcp)) {
3536 printxval(schedulers, tcp->u_arg[0], "SCHED_???");
3537 }
3538 return 0;
3539}
Roland McGrathc2d5eb02005-02-02 04:16:56 +00003540
3541#ifdef X86_64
3542#include <asm/prctl.h>
3543
3544static const struct xlat archvals[] = {
3545 { ARCH_SET_GS, "ARCH_SET_GS" },
3546 { ARCH_SET_FS, "ARCH_SET_FS" },
3547 { ARCH_GET_FS, "ARCH_GET_FS" },
3548 { ARCH_GET_GS, "ARCH_GET_GS" },
3549 { 0, NULL },
3550};
3551
3552int
3553sys_arch_prctl(tcp)
3554struct tcb *tcp;
3555{
3556 if (entering(tcp)) {
3557 printxval(archvals, tcp->u_arg[0], "ARCH_???");
3558 if (tcp->u_arg[0] == ARCH_SET_GS
3559 || tcp->u_arg[0] == ARCH_SET_FS)
3560 tprintf(", %#lx", tcp->u_arg[1]);
3561 } else {
3562 if (tcp->u_arg[0] == ARCH_GET_GS
3563 || tcp->u_arg[0] == ARCH_GET_FS) {
3564 long int v;
3565 if (!syserror(tcp) && umove(tcp, tcp->u_arg[1], &v) != -1)
3566 tprintf(", [%#lx]", v);
3567 else
3568 tprintf(", %#lx", tcp->u_arg[1]);
3569 }
3570 }
3571 return 0;
3572}
3573#endif
3574
Roland McGrathdb8319f2007-08-02 01:37:55 +00003575
3576int
3577sys_getcpu(tcp)
3578struct tcb *tcp;
3579{
3580 if (exiting(tcp)) {
3581 unsigned u;
3582 if (tcp->u_arg[0] == 0)
3583 tprintf("NULL, ");
3584 else if (umove(tcp, tcp->u_arg[0], &u) < 0)
3585 tprintf("%#lx, ", tcp->u_arg[0]);
3586 else
3587 tprintf("[%u], ", u);
3588 if (tcp->u_arg[1] == 0)
3589 tprintf("NULL, ");
3590 else if (umove(tcp, tcp->u_arg[1], &u) < 0)
3591 tprintf("%#lx, ", tcp->u_arg[1]);
3592 else
3593 tprintf("[%u], ", u);
3594 tprintf("%#lx", tcp->u_arg[2]);
3595 }
3596 return 0;
3597}
3598
Roland McGrath5a223472002-12-15 23:58:26 +00003599#endif