* solib-svr4.c (LM_ADDR_FROM_LINK_MAP): Use builtin types of
[deliverable/binutils-gdb.git] / gdb / inf-ptrace.c
CommitLineData
2c4a536d 1/* Low-level child interface to ptrace.
5bf970f9 2
6aba47ca 3 Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998,
9b254dd1 4 1999, 2000, 2001, 2002, 2004, 2005, 2006, 2007, 2008
8785ced0 5 Free Software Foundation, Inc.
5bf970f9
AC
6
7 This file is part of GDB.
8
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
a9762ec7 11 the Free Software Foundation; either version 3 of the License, or
5bf970f9
AC
12 (at your option) any later version.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
a9762ec7 20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
5bf970f9
AC
21
22#include "defs.h"
5bf970f9 23#include "command.h"
2c4a536d
MK
24#include "inferior.h"
25#include "inflow.h"
5bf970f9 26#include "gdbcore.h"
8785ced0 27#include "regcache.h"
5bf970f9 28
8785ced0 29#include "gdb_assert.h"
2c4a536d
MK
30#include "gdb_string.h"
31#include "gdb_ptrace.h"
34a17005 32#include "gdb_wait.h"
5bf970f9
AC
33#include <signal.h>
34
2c4a536d 35#include "inf-child.h"
af990527 36#include "gdbthread.h"
2c4a536d
MK
37
38/* HACK: Save the ptrace ops returned by inf_ptrace_target. */
5bf970f9 39static struct target_ops *ptrace_ops_hack;
c7c14b96
MK
40\f
41
735f54b4
MK
42#ifdef PT_GET_PROCESS_STATE
43
44static int
ee057212 45inf_ptrace_follow_fork (struct target_ops *ops, int follow_child)
735f54b4
MK
46{
47 pid_t pid, fpid;
48 ptrace_state_t pe;
4e1c45ea 49 struct thread_info *last_tp = NULL;
735f54b4
MK
50
51 /* FIXME: kettenis/20050720: This stuff should really be passed as
52 an argument by our caller. */
53 {
54 ptid_t ptid;
55 struct target_waitstatus status;
56
57 get_last_target_status (&ptid, &status);
58 gdb_assert (status.kind == TARGET_WAITKIND_FORKED);
59
60 pid = ptid_get_pid (ptid);
4e1c45ea 61 last_tp = find_thread_pid (ptid);
735f54b4
MK
62 }
63
64 if (ptrace (PT_GET_PROCESS_STATE, pid,
65 (PTRACE_TYPE_ARG3)&pe, sizeof pe) == -1)
66 perror_with_name (("ptrace"));
67
68 gdb_assert (pe.pe_report_event == PTRACE_FORK);
69 fpid = pe.pe_other_pid;
70
71 if (follow_child)
72 {
4e1c45ea
PA
73 /* Copy user stepping state to the new inferior thread. */
74 struct breakpoint *step_resume_breakpoint = last_tp->step_resume_breakpoint;
75 CORE_ADDR step_range_start = last_tp->step_range_start;
76 CORE_ADDR step_range_end = last_tp->step_range_end;
77 struct frame_id step_frame_id = last_tp->step_frame_id;
735f54b4 78
4e1c45ea
PA
79 struct thread_info *tp;
80
81 /* Otherwise, deleting the parent would get rid of this
82 breakpoint. */
83 last_tp->step_resume_breakpoint = NULL;
84
85 /* Before detaching from the parent, remove all breakpoints from
86 it. */
87 detach_breakpoints (pid);
735f54b4
MK
88
89 if (ptrace (PT_DETACH, pid, (PTRACE_TYPE_ARG3)1, 0) == -1)
90 perror_with_name (("ptrace"));
4e1c45ea
PA
91
92 /* Delete the parent. */
93 delete_thread_silent (last_tp->ptid);
94
95 /* Add the child. */
96 inferior_ptid = pid_to_ptid (fpid);
97 tp = add_thread_silent (inferior_ptid);
98
99 tp->step_resume_breakpoint = step_resume_breakpoint;
100 tp->step_range_start = step_range_start;
101 tp->step_range_end = step_range_end;
102 tp->step_frame_id = step_frame_id;
103
104 /* Reset breakpoints in the child as appropriate. */
105 follow_inferior_reset_breakpoints ();
735f54b4
MK
106 }
107 else
108 {
109 inferior_ptid = pid_to_ptid (pid);
110 detach_breakpoints (fpid);
111
112 if (ptrace (PT_DETACH, fpid, (PTRACE_TYPE_ARG3)1, 0) == -1)
113 perror_with_name (("ptrace"));
114 }
115
116 return 0;
117}
118
119#endif /* PT_GET_PROCESS_STATE */
120\f
121
4b8a1a28 122/* Prepare to be traced. */
5bf970f9
AC
123
124static void
c7c14b96 125inf_ptrace_me (void)
5bf970f9 126{
c7c14b96 127 /* "Trace me, Dr. Memory!" */
4b8a1a28 128 ptrace (PT_TRACE_ME, 0, (PTRACE_TYPE_ARG3)0, 0);
5bf970f9
AC
129}
130
4b8a1a28 131/* Start tracing PID. */
5bf970f9
AC
132
133static void
c7c14b96 134inf_ptrace_him (int pid)
5bf970f9 135{
c7c14b96 136 push_target (ptrace_ops_hack);
5bf970f9 137
c7c14b96
MK
138 /* On some targets, there must be some explicit synchronization
139 between the parent and child processes after the debugger
140 forks, and before the child execs the debuggee program. This
141 call basically gives permission for the child to exec. */
5bf970f9 142
c7c14b96 143 target_acknowledge_created_inferior (pid);
5bf970f9 144
c7c14b96
MK
145 /* START_INFERIOR_TRAPS_EXPECTED is defined in inferior.h, and will
146 be 1 or 2 depending on whether we're starting without or with a
147 shell. */
148 startup_inferior (START_INFERIOR_TRAPS_EXPECTED);
149
150 /* On some targets, there must be some explicit actions taken after
151 the inferior has been started up. */
152 target_post_startup_inferior (pid_to_ptid (pid));
5bf970f9
AC
153}
154
4b8a1a28
MK
155/* Start a new inferior Unix child process. EXEC_FILE is the file to
156 run, ALLARGS is a string containing the arguments to the program.
157 ENV is the environment vector to pass. If FROM_TTY is non-zero, be
158 chatty about it. */
5bf970f9 159
c7c14b96
MK
160static void
161inf_ptrace_create_inferior (char *exec_file, char *allargs, char **env,
162 int from_tty)
5bf970f9 163{
c7c14b96
MK
164 fork_inferior (exec_file, allargs, env, inf_ptrace_me, inf_ptrace_him,
165 NULL, NULL);
5bf970f9
AC
166}
167
e4ef629d
MK
168#ifdef PT_GET_PROCESS_STATE
169
170static void
171inf_ptrace_post_startup_inferior (ptid_t pid)
172{
173 ptrace_event_t pe;
174
175 /* Set the initial event mask. */
176 memset (&pe, 0, sizeof pe);
177 pe.pe_set_event |= PTRACE_FORK;
178 if (ptrace (PT_SET_EVENT_MASK, ptid_get_pid (pid),
179 (PTRACE_TYPE_ARG3)&pe, sizeof pe) == -1)
180 perror_with_name (("ptrace"));
181}
182
183#endif
184
4b8a1a28
MK
185/* Clean up a rotting corpse of an inferior after it died. */
186
c7c14b96
MK
187static void
188inf_ptrace_mourn_inferior (void)
5bf970f9 189{
4b8a1a28
MK
190 int status;
191
192 /* Wait just one more time to collect the inferior's exit status.
f010475d 193 Do not check whether this succeeds though, since we may be
4b8a1a28 194 dealing with a process that we attached to. Such a process will
3d450bdd 195 only report its exit status to its original parent. */
4b8a1a28
MK
196 waitpid (ptid_get_pid (inferior_ptid), &status, 0);
197
c7c14b96
MK
198 unpush_target (ptrace_ops_hack);
199 generic_mourn_inferior ();
5bf970f9
AC
200}
201
4b8a1a28
MK
202/* Attach to the process specified by ARGS. If FROM_TTY is non-zero,
203 be chatty about it. */
5bf970f9
AC
204
205static void
206inf_ptrace_attach (char *args, int from_tty)
207{
208 char *exec_file;
4b8a1a28 209 pid_t pid;
5bf970f9
AC
210 char *dummy;
211
212 if (!args)
e2e0b3e5 213 error_no_arg (_("process-id to attach"));
5bf970f9
AC
214
215 dummy = args;
216 pid = strtol (args, &dummy, 0);
f6ffd89b 217 /* Some targets don't set errno on errors, grrr! */
6e1e94ea 218 if (pid == 0 && args == dummy)
8a3fe4f8 219 error (_("Illegal process-id: %s."), args);
5bf970f9 220
f6ffd89b 221 if (pid == getpid ()) /* Trying to masturbate? */
8a3fe4f8 222 error (_("I refuse to debug myself!"));
5bf970f9
AC
223
224 if (from_tty)
225 {
4b8a1a28 226 exec_file = get_exec_file (0);
5bf970f9
AC
227
228 if (exec_file)
a3f17187 229 printf_unfiltered (_("Attaching to program: %s, %s\n"), exec_file,
5bf970f9
AC
230 target_pid_to_str (pid_to_ptid (pid)));
231 else
a3f17187 232 printf_unfiltered (_("Attaching to %s\n"),
5bf970f9
AC
233 target_pid_to_str (pid_to_ptid (pid)));
234
235 gdb_flush (gdb_stdout);
236 }
237
6e1e94ea
MK
238#ifdef PT_ATTACH
239 errno = 0;
4b8a1a28 240 ptrace (PT_ATTACH, pid, (PTRACE_TYPE_ARG3)0, 0);
6e1e94ea 241 if (errno != 0)
e2e0b3e5 242 perror_with_name (("ptrace"));
6e1e94ea
MK
243 attach_flag = 1;
244#else
8a3fe4f8 245 error (_("This system does not support attaching to a process"));
6e1e94ea 246#endif
5bf970f9
AC
247
248 inferior_ptid = pid_to_ptid (pid);
af990527
PA
249
250 /* Always add a main thread. If some target extends the ptrace
251 target, it should decorate the ptid later with more info. */
252 add_thread_silent (inferior_ptid);
253
5bf970f9
AC
254 push_target (ptrace_ops_hack);
255}
256
e4ef629d
MK
257#ifdef PT_GET_PROCESS_STATE
258
259void
260inf_ptrace_post_attach (int pid)
261{
262 ptrace_event_t pe;
263
264 /* Set the initial event mask. */
265 memset (&pe, 0, sizeof pe);
266 pe.pe_set_event |= PTRACE_FORK;
267 if (ptrace (PT_SET_EVENT_MASK, pid,
268 (PTRACE_TYPE_ARG3)&pe, sizeof pe) == -1)
269 perror_with_name (("ptrace"));
270}
271
272#endif
273
4b8a1a28 274/* Detach from the inferior, optionally passing it the signal
f010475d 275 specified by ARGS. If FROM_TTY is non-zero, be chatty about it. */
5bf970f9
AC
276
277static void
278inf_ptrace_detach (char *args, int from_tty)
279{
4b8a1a28 280 pid_t pid = ptid_get_pid (inferior_ptid);
6e1e94ea 281 int sig = 0;
5bf970f9
AC
282
283 if (from_tty)
284 {
285 char *exec_file = get_exec_file (0);
286 if (exec_file == 0)
287 exec_file = "";
a3f17187 288 printf_unfiltered (_("Detaching from program: %s, %s\n"), exec_file,
5bf970f9
AC
289 target_pid_to_str (pid_to_ptid (pid)));
290 gdb_flush (gdb_stdout);
291 }
292 if (args)
6e1e94ea 293 sig = atoi (args);
5bf970f9 294
6e1e94ea 295#ifdef PT_DETACH
4b8a1a28 296 /* We'd better not have left any breakpoints in the program or it'll
f010475d 297 die when it hits one. Also note that this may only work if we
4b8a1a28
MK
298 previously attached to the inferior. It *might* work if we
299 started the process ourselves. */
6e1e94ea 300 errno = 0;
4b8a1a28 301 ptrace (PT_DETACH, pid, (PTRACE_TYPE_ARG3)1, sig);
6e1e94ea 302 if (errno != 0)
e2e0b3e5 303 perror_with_name (("ptrace"));
6e1e94ea
MK
304 attach_flag = 0;
305#else
8a3fe4f8 306 error (_("This system does not support detaching from a process"));
6e1e94ea 307#endif
5bf970f9
AC
308
309 inferior_ptid = null_ptid;
310 unpush_target (ptrace_ops_hack);
311}
312
4b8a1a28
MK
313/* Kill the inferior. */
314
5bf970f9 315static void
4b8a1a28 316inf_ptrace_kill (void)
5bf970f9 317{
4b8a1a28 318 pid_t pid = ptid_get_pid (inferior_ptid);
c7c14b96 319 int status;
c7c14b96
MK
320
321 if (pid == 0)
322 return;
323
4b8a1a28
MK
324 ptrace (PT_KILL, pid, (PTRACE_TYPE_ARG3)0, 0);
325 waitpid (pid, &status, 0);
326
c7c14b96 327 target_mourn_inferior ();
5bf970f9
AC
328}
329
4b8a1a28 330/* Stop the inferior. */
c7c14b96 331
5bf970f9 332static void
94cc34af 333inf_ptrace_stop (ptid_t ptid)
5bf970f9 334{
4b8a1a28
MK
335 /* Send a SIGINT to the process group. This acts just like the user
336 typed a ^C on the controlling terminal. Note that using a
337 negative process number in kill() is a System V-ism. The proper
338 BSD interface is killpg(). However, all modern BSDs support the
339 System V interface too. */
c7c14b96 340 kill (-inferior_process_group, SIGINT);
5bf970f9
AC
341}
342
4b8a1a28
MK
343/* Resume execution of thread PTID, or all threads if PTID is -1. If
344 STEP is nonzero, single-step it. If SIGNAL is nonzero, give it
345 that signal. */
5bf970f9
AC
346
347static void
c7c14b96 348inf_ptrace_resume (ptid_t ptid, int step, enum target_signal signal)
5bf970f9 349{
4b8a1a28 350 pid_t pid = ptid_get_pid (ptid);
c7c14b96 351 int request = PT_CONTINUE;
c7c14b96
MK
352
353 if (pid == -1)
4b8a1a28
MK
354 /* Resume all threads. Traditionally ptrace() only supports
355 single-threaded processes, so simply resume the inferior. */
356 pid = ptid_get_pid (inferior_ptid);
c7c14b96
MK
357
358 if (step)
359 {
360 /* If this system does not support PT_STEP, a higher level
361 function will have called single_step() to transmute the step
362 request into a continue request (by setting breakpoints on
363 all possible successor instructions), so we don't have to
364 worry about that here. */
365 request = PT_STEP;
366 }
367
368 /* An address of (PTRACE_TYPE_ARG3)1 tells ptrace to continue from
369 where it was. If GDB wanted it to start some other way, we have
4b8a1a28 370 already written a new program counter value to the child. */
c7c14b96 371 errno = 0;
4b8a1a28 372 ptrace (request, pid, (PTRACE_TYPE_ARG3)1, target_signal_to_host (signal));
c7c14b96
MK
373 if (errno != 0)
374 perror_with_name (("ptrace"));
5bf970f9
AC
375}
376
4b8a1a28
MK
377/* Wait for the child specified by PTID to do something. Return the
378 process ID of the child, or MINUS_ONE_PTID in case of error; store
379 the status in *OURSTATUS. */
5bf970f9 380
c7c14b96
MK
381static ptid_t
382inf_ptrace_wait (ptid_t ptid, struct target_waitstatus *ourstatus)
5bf970f9 383{
4b8a1a28
MK
384 pid_t pid;
385 int status, save_errno;
5bf970f9 386
c7c14b96
MK
387 do
388 {
4b8a1a28 389 set_sigint_trap ();
c7c14b96 390 set_sigio_trap ();
5bf970f9 391
4b8a1a28
MK
392 do
393 {
394 pid = waitpid (ptid_get_pid (ptid), &status, 0);
395 save_errno = errno;
396 }
397 while (pid == -1 && errno == EINTR);
5bf970f9 398
c7c14b96 399 clear_sigio_trap ();
c7c14b96 400 clear_sigint_trap ();
5bf970f9 401
c7c14b96
MK
402 if (pid == -1)
403 {
c7c14b96 404 fprintf_unfiltered (gdb_stderr,
4b8a1a28 405 _("Child process unexpectedly missing: %s.\n"),
c7c14b96
MK
406 safe_strerror (save_errno));
407
408 /* Claim it exited with unknown signal. */
409 ourstatus->kind = TARGET_WAITKIND_SIGNALLED;
410 ourstatus->value.sig = TARGET_SIGNAL_UNKNOWN;
4b8a1a28 411 return minus_one_ptid;
c7c14b96
MK
412 }
413
4b8a1a28
MK
414 /* Ignore terminated detached child processes. */
415 if (!WIFSTOPPED (status) && pid != ptid_get_pid (inferior_ptid))
416 pid = -1;
c7c14b96 417 }
4b8a1a28 418 while (pid == -1);
c7c14b96 419
735f54b4
MK
420#ifdef PT_GET_PROCESS_STATE
421 if (WIFSTOPPED (status))
422 {
423 ptrace_state_t pe;
424 pid_t fpid;
425
426 if (ptrace (PT_GET_PROCESS_STATE, pid,
427 (PTRACE_TYPE_ARG3)&pe, sizeof pe) == -1)
428 perror_with_name (("ptrace"));
429
430 switch (pe.pe_report_event)
431 {
432 case PTRACE_FORK:
433 ourstatus->kind = TARGET_WAITKIND_FORKED;
3a3e9ee3 434 ourstatus->value.related_pid = pid_to_ptid (pe.pe_other_pid);
735f54b4
MK
435
436 /* Make sure the other end of the fork is stopped too. */
437 fpid = waitpid (pe.pe_other_pid, &status, 0);
438 if (fpid == -1)
439 perror_with_name (("waitpid"));
440
441 if (ptrace (PT_GET_PROCESS_STATE, fpid,
442 (PTRACE_TYPE_ARG3)&pe, sizeof pe) == -1)
443 perror_with_name (("ptrace"));
444
445 gdb_assert (pe.pe_report_event == PTRACE_FORK);
446 gdb_assert (pe.pe_other_pid == pid);
447 if (fpid == ptid_get_pid (inferior_ptid))
448 {
3a3e9ee3 449 ourstatus->value.related_pid = pid_to_ptid (pe.pe_other_pid);
735f54b4
MK
450 return pid_to_ptid (fpid);
451 }
452
453 return pid_to_ptid (pid);
454 }
455 }
456#endif
457
c7c14b96
MK
458 store_waitstatus (ourstatus, status);
459 return pid_to_ptid (pid);
5bf970f9
AC
460}
461
4b8a1a28
MK
462/* Attempt a transfer all LEN bytes starting at OFFSET between the
463 inferior's OBJECT:ANNEX space and GDB's READBUF/WRITEBUF buffer.
464 Return the number of bytes actually transferred. */
5bf970f9
AC
465
466static LONGEST
467inf_ptrace_xfer_partial (struct target_ops *ops, enum target_object object,
961cb7b5
MK
468 const char *annex, gdb_byte *readbuf,
469 const gdb_byte *writebuf,
470 ULONGEST offset, LONGEST len)
5bf970f9 471{
4b8a1a28
MK
472 pid_t pid = ptid_get_pid (inferior_ptid);
473
5bf970f9
AC
474 switch (object)
475 {
476 case TARGET_OBJECT_MEMORY:
f929a579
AC
477#ifdef PT_IO
478 /* OpenBSD 3.1, NetBSD 1.6 and FreeBSD 5.0 have a new PT_IO
479 request that promises to be much more efficient in reading
480 and writing data in the traced process's address space. */
481 {
482 struct ptrace_io_desc piod;
4b8a1a28 483
f929a579 484 /* NOTE: We assume that there are no distinct address spaces
b457b3dd
MK
485 for instruction and data. However, on OpenBSD 3.9 and
486 later, PIOD_WRITE_D doesn't allow changing memory that's
487 mapped read-only. Since most code segments will be
488 read-only, using PIOD_WRITE_D will prevent us from
489 inserting breakpoints, so we use PIOD_WRITE_I instead. */
490 piod.piod_op = writebuf ? PIOD_WRITE_I : PIOD_READ_D;
f929a579
AC
491 piod.piod_addr = writebuf ? (void *) writebuf : readbuf;
492 piod.piod_offs = (void *) (long) offset;
493 piod.piod_len = len;
494
495 errno = 0;
4b8a1a28 496 if (ptrace (PT_IO, pid, (caddr_t)&piod, 0) == 0)
f929a579
AC
497 /* Return the actual number of bytes read or written. */
498 return piod.piod_len;
499 /* If the PT_IO request is somehow not supported, fallback on
500 using PT_WRITE_D/PT_READ_D. Otherwise we will return zero
501 to indicate failure. */
502 if (errno != EINVAL)
503 return 0;
504 }
505#endif
506 {
507 union
508 {
509 PTRACE_TYPE_RET word;
4b8a1a28 510 gdb_byte byte[sizeof (PTRACE_TYPE_RET)];
f929a579
AC
511 } buffer;
512 ULONGEST rounded_offset;
513 LONGEST partial_len;
4b8a1a28 514
cb85a953
AC
515 /* Round the start offset down to the next long word
516 boundary. */
f929a579 517 rounded_offset = offset & -(ULONGEST) sizeof (PTRACE_TYPE_RET);
4b8a1a28 518
cb85a953
AC
519 /* Since ptrace will transfer a single word starting at that
520 rounded_offset the partial_len needs to be adjusted down to
521 that (remember this function only does a single transfer).
522 Should the required length be even less, adjust it down
523 again. */
524 partial_len = (rounded_offset + sizeof (PTRACE_TYPE_RET)) - offset;
525 if (partial_len > len)
f929a579 526 partial_len = len;
4b8a1a28 527
f929a579
AC
528 if (writebuf)
529 {
cb85a953
AC
530 /* If OFFSET:PARTIAL_LEN is smaller than
531 ROUNDED_OFFSET:WORDSIZE then a read/modify write will
532 be needed. Read in the entire word. */
f929a579 533 if (rounded_offset < offset
cb85a953
AC
534 || (offset + partial_len
535 < rounded_offset + sizeof (PTRACE_TYPE_RET)))
f929a579 536 /* Need part of initial word -- fetch it. */
4b8a1a28 537 buffer.word = ptrace (PT_READ_I, pid,
f7dd0ed7
UW
538 (PTRACE_TYPE_ARG3)(uintptr_t)
539 rounded_offset, 0);
4b8a1a28 540
f929a579
AC
541 /* Copy data to be written over corresponding part of
542 buffer. */
f6ffd89b
MK
543 memcpy (buffer.byte + (offset - rounded_offset),
544 writebuf, partial_len);
4b8a1a28 545
f929a579 546 errno = 0;
4b8a1a28 547 ptrace (PT_WRITE_D, pid,
f7dd0ed7
UW
548 (PTRACE_TYPE_ARG3)(uintptr_t)rounded_offset,
549 buffer.word);
f929a579
AC
550 if (errno)
551 {
552 /* Using the appropriate one (I or D) is necessary for
553 Gould NP1, at least. */
554 errno = 0;
4b8a1a28 555 ptrace (PT_WRITE_I, pid,
f7dd0ed7
UW
556 (PTRACE_TYPE_ARG3)(uintptr_t)rounded_offset,
557 buffer.word);
f929a579
AC
558 if (errno)
559 return 0;
560 }
561 }
4b8a1a28 562
f929a579
AC
563 if (readbuf)
564 {
565 errno = 0;
4b8a1a28 566 buffer.word = ptrace (PT_READ_I, pid,
f7dd0ed7
UW
567 (PTRACE_TYPE_ARG3)(uintptr_t)rounded_offset,
568 0);
f929a579
AC
569 if (errno)
570 return 0;
571 /* Copy appropriate bytes out of the buffer. */
572 memcpy (readbuf, buffer.byte + (offset - rounded_offset),
573 partial_len);
574 }
4b8a1a28 575
f929a579
AC
576 return partial_len;
577 }
5bf970f9
AC
578
579 case TARGET_OBJECT_UNWIND_TABLE:
580 return -1;
581
582 case TARGET_OBJECT_AUXV:
583 return -1;
584
585 case TARGET_OBJECT_WCOOKIE:
586 return -1;
587
588 default:
589 return -1;
590 }
591}
592
4b8a1a28 593/* Return non-zero if the thread specified by PTID is alive. */
c7c14b96
MK
594
595static int
596inf_ptrace_thread_alive (ptid_t ptid)
597{
4b8a1a28
MK
598 /* ??? Is kill the right way to do this? */
599 return (kill (ptid_get_pid (ptid), 0) != -1);
c7c14b96
MK
600}
601
602/* Print status information about what we're accessing. */
603
604static void
605inf_ptrace_files_info (struct target_ops *ignore)
606{
4b8a1a28
MK
607 printf_filtered (_("\tUsing the running image of %s %s.\n"),
608 attach_flag ? "attached" : "child",
609 target_pid_to_str (inferior_ptid));
5bf970f9
AC
610}
611
8785ced0
MK
612/* Create a prototype ptrace target. The client can override it with
613 local methods. */
614
5bf970f9
AC
615struct target_ops *
616inf_ptrace_target (void)
617{
618 struct target_ops *t = inf_child_target ();
8785ced0 619
5bf970f9 620 t->to_attach = inf_ptrace_attach;
5bf970f9
AC
621 t->to_detach = inf_ptrace_detach;
622 t->to_resume = inf_ptrace_resume;
623 t->to_wait = inf_ptrace_wait;
5bf970f9 624 t->to_files_info = inf_ptrace_files_info;
4b8a1a28 625 t->to_kill = inf_ptrace_kill;
5bf970f9 626 t->to_create_inferior = inf_ptrace_create_inferior;
735f54b4
MK
627#ifdef PT_GET_PROCESS_STATE
628 t->to_follow_fork = inf_ptrace_follow_fork;
e4ef629d
MK
629 t->to_post_startup_inferior = inf_ptrace_post_startup_inferior;
630 t->to_post_attach = inf_ptrace_post_attach;
735f54b4 631#endif
5bf970f9 632 t->to_mourn_inferior = inf_ptrace_mourn_inferior;
5bf970f9 633 t->to_thread_alive = inf_ptrace_thread_alive;
4b8a1a28 634 t->to_pid_to_str = normal_pid_to_str;
5bf970f9 635 t->to_stop = inf_ptrace_stop;
c7c14b96 636 t->to_xfer_partial = inf_ptrace_xfer_partial;
8785ced0 637
c7c14b96 638 ptrace_ops_hack = t;
8785ced0
MK
639 return t;
640}
641\f
642
4b8a1a28 643/* Pointer to a function that returns the offset within the user area
8785ced0 644 where a particular register is stored. */
7714d83a 645static CORE_ADDR (*inf_ptrace_register_u_offset)(struct gdbarch *, int, int);
8785ced0
MK
646
647/* Fetch register REGNUM from the inferior. */
648
649static void
56be3814 650inf_ptrace_fetch_register (struct regcache *regcache, int regnum)
8785ced0 651{
3b3b1423 652 struct gdbarch *gdbarch = get_regcache_arch (regcache);
8785ced0
MK
653 CORE_ADDR addr;
654 size_t size;
655 PTRACE_TYPE_RET *buf;
656 int pid, i;
657
7714d83a 658 /* This isn't really an address, but ptrace thinks of it as one. */
3b3b1423 659 addr = inf_ptrace_register_u_offset (gdbarch, regnum, 0);
8d4c1ba3 660 if (addr == (CORE_ADDR)-1
3b3b1423 661 || gdbarch_cannot_fetch_register (gdbarch, regnum))
10d6c8cd 662 {
56be3814 663 regcache_raw_supply (regcache, regnum, NULL);
10d6c8cd
DJ
664 return;
665 }
666
8785ced0 667 /* Cater for systems like GNU/Linux, that implement threads as
10d6c8cd 668 separate processes. */
8785ced0
MK
669 pid = ptid_get_lwp (inferior_ptid);
670 if (pid == 0)
671 pid = ptid_get_pid (inferior_ptid);
672
3b3b1423 673 size = register_size (gdbarch, regnum);
8785ced0
MK
674 gdb_assert ((size % sizeof (PTRACE_TYPE_RET)) == 0);
675 buf = alloca (size);
676
10d6c8cd 677 /* Read the register contents from the inferior a chunk at a time. */
8785ced0
MK
678 for (i = 0; i < size / sizeof (PTRACE_TYPE_RET); i++)
679 {
680 errno = 0;
f7dd0ed7 681 buf[i] = ptrace (PT_READ_U, pid, (PTRACE_TYPE_ARG3)(uintptr_t)addr, 0);
8785ced0 682 if (errno != 0)
4b8a1a28 683 error (_("Couldn't read register %s (#%d): %s."),
3b3b1423 684 gdbarch_register_name (gdbarch, regnum),
c9f4d572 685 regnum, safe_strerror (errno));
8785ced0
MK
686
687 addr += sizeof (PTRACE_TYPE_RET);
688 }
56be3814 689 regcache_raw_supply (regcache, regnum, buf);
8785ced0
MK
690}
691
692/* Fetch register REGNUM from the inferior. If REGNUM is -1, do this
693 for all registers. */
694
695static void
56be3814 696inf_ptrace_fetch_registers (struct regcache *regcache, int regnum)
8785ced0
MK
697{
698 if (regnum == -1)
3b3b1423
UW
699 for (regnum = 0;
700 regnum < gdbarch_num_regs (get_regcache_arch (regcache));
701 regnum++)
56be3814 702 inf_ptrace_fetch_register (regcache, regnum);
8785ced0 703 else
56be3814 704 inf_ptrace_fetch_register (regcache, regnum);
8785ced0
MK
705}
706
707/* Store register REGNUM into the inferior. */
708
709static void
56be3814 710inf_ptrace_store_register (const struct regcache *regcache, int regnum)
8785ced0 711{
3b3b1423 712 struct gdbarch *gdbarch = get_regcache_arch (regcache);
8785ced0
MK
713 CORE_ADDR addr;
714 size_t size;
715 PTRACE_TYPE_RET *buf;
716 int pid, i;
717
7714d83a 718 /* This isn't really an address, but ptrace thinks of it as one. */
3b3b1423 719 addr = inf_ptrace_register_u_offset (gdbarch, regnum, 1);
8d4c1ba3 720 if (addr == (CORE_ADDR)-1
3b3b1423 721 || gdbarch_cannot_store_register (gdbarch, regnum))
10d6c8cd
DJ
722 return;
723
8785ced0 724 /* Cater for systems like GNU/Linux, that implement threads as
10d6c8cd 725 separate processes. */
8785ced0
MK
726 pid = ptid_get_lwp (inferior_ptid);
727 if (pid == 0)
728 pid = ptid_get_pid (inferior_ptid);
729
3b3b1423 730 size = register_size (gdbarch, regnum);
8785ced0
MK
731 gdb_assert ((size % sizeof (PTRACE_TYPE_RET)) == 0);
732 buf = alloca (size);
733
10d6c8cd 734 /* Write the register contents into the inferior a chunk at a time. */
56be3814 735 regcache_raw_collect (regcache, regnum, buf);
8785ced0
MK
736 for (i = 0; i < size / sizeof (PTRACE_TYPE_RET); i++)
737 {
738 errno = 0;
f7dd0ed7 739 ptrace (PT_WRITE_U, pid, (PTRACE_TYPE_ARG3)(uintptr_t)addr, buf[i]);
8785ced0 740 if (errno != 0)
4b8a1a28 741 error (_("Couldn't write register %s (#%d): %s."),
3b3b1423 742 gdbarch_register_name (gdbarch, regnum),
c9f4d572 743 regnum, safe_strerror (errno));
8785ced0
MK
744
745 addr += sizeof (PTRACE_TYPE_RET);
746 }
747}
748
749/* Store register REGNUM back into the inferior. If REGNUM is -1, do
750 this for all registers. */
751
752void
56be3814 753inf_ptrace_store_registers (struct regcache *regcache, int regnum)
8785ced0
MK
754{
755 if (regnum == -1)
3b3b1423
UW
756 for (regnum = 0;
757 regnum < gdbarch_num_regs (get_regcache_arch (regcache));
758 regnum++)
56be3814 759 inf_ptrace_store_register (regcache, regnum);
8785ced0 760 else
56be3814 761 inf_ptrace_store_register (regcache, regnum);
8785ced0
MK
762}
763
764/* Create a "traditional" ptrace target. REGISTER_U_OFFSET should be
765 a function returning the offset within the user area where a
766 particular register is stored. */
767
768struct target_ops *
7714d83a
UW
769inf_ptrace_trad_target (CORE_ADDR (*register_u_offset)
770 (struct gdbarch *, int, int))
8785ced0
MK
771{
772 struct target_ops *t = inf_ptrace_target();
773
774 gdb_assert (register_u_offset);
775 inf_ptrace_register_u_offset = register_u_offset;
776 t->to_fetch_registers = inf_ptrace_fetch_registers;
777 t->to_store_registers = inf_ptrace_store_registers;
778
5bf970f9
AC
779 return t;
780}
This page took 0.36605 seconds and 4 git commands to generate.