* target.h: Add enum target_waitkind, enum target_signal, and
[deliverable/binutils-gdb.git] / gdb / inftarg.c
CommitLineData
3aa6856a 1/* Target-vector operations for controlling Unix child processes, for GDB.
310cc570 2 Copyright 1990, 1991, 1992 Free Software Foundation, Inc.
bd5635a1
RP
3 Contributed by Cygnus Support.
4
5This file is part of GDB.
6
dcc8abce 7This program is free software; you can redistribute it and/or modify
bd5635a1 8it under the terms of the GNU General Public License as published by
dcc8abce
JG
9the Free Software Foundation; either version 2 of the License, or
10(at your option) any later version.
bd5635a1 11
dcc8abce 12This program is distributed in the hope that it will be useful,
bd5635a1
RP
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
dcc8abce
JG
18along with this program; if not, write to the Free Software
19Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
bd5635a1 20
bd5635a1 21#include "defs.h"
bd5635a1
RP
22#include "frame.h" /* required by inferior.h */
23#include "inferior.h"
24#include "target.h"
25#include "wait.h"
26#include "gdbcore.h"
100f92e2 27#include "command.h"
310cc570
RP
28#include <signal.h>
29
dcc8abce
JG
30static void
31child_prepare_to_store PARAMS ((void));
32
de43d7d0 33#ifndef CHILD_WAIT
dcc8abce 34static int
67ac9759 35child_wait PARAMS ((int, struct target_waitstatus *));
de43d7d0 36#endif /* CHILD_WAIT */
dcc8abce
JG
37
38static void
39child_open PARAMS ((char *, int));
40
41static void
42child_files_info PARAMS ((struct target_ops *));
43
44static void
45child_detach PARAMS ((char *, int));
bd5635a1 46
310cc570
RP
47static void
48child_attach PARAMS ((char *, int));
49
de43d7d0
SG
50static void
51ptrace_me PARAMS ((void));
52
53static void
54ptrace_him PARAMS ((int));
55
310cc570
RP
56static void
57child_create_inferior PARAMS ((char *, char *, char **));
58
59static void
60child_mourn_inferior PARAMS ((void));
61
3aa6856a
JG
62static int
63child_can_run PARAMS ((void));
64
310cc570
RP
65extern char **environ;
66
bd5635a1
RP
67/* Forward declaration */
68extern struct target_ops child_ops;
69
67ac9759
JK
70/* Convert host signal to our signals. */
71enum target_signal
72target_signal_from_host (hostsig)
73 int hostsig;
74{
75 /* A switch statement would make sense but would require special kludges
76 to deal with the cases where more than one signal has the same number. */
77
78 if (hostsig == 0) return TARGET_SIGNAL_0;
79
80#if defined (SIGHUP)
81 if (hostsig == SIGHUP) return TARGET_SIGNAL_HUP;
82#endif
83#if defined (SIGINT)
84 if (hostsig == SIGINT) return TARGET_SIGNAL_INT;
85#endif
86#if defined (SIGQUIT)
87 if (hostsig == SIGQUIT) return TARGET_SIGNAL_QUIT;
88#endif
89#if defined (SIGILL)
90 if (hostsig == SIGILL) return TARGET_SIGNAL_ILL;
91#endif
92#if defined (SIGTRAP)
93 if (hostsig == SIGTRAP) return TARGET_SIGNAL_TRAP;
94#endif
95#if defined (SIGABRT)
96 if (hostsig == SIGABRT) return TARGET_SIGNAL_ABRT;
97#endif
98#if defined (SIGEMT)
99 if (hostsig == SIGEMT) return TARGET_SIGNAL_EMT;
100#endif
101#if defined (SIGFPE)
102 if (hostsig == SIGFPE) return TARGET_SIGNAL_FPE;
103#endif
104#if defined (SIGKILL)
105 if (hostsig == SIGKILL) return TARGET_SIGNAL_KILL;
106#endif
107#if defined (SIGBUS)
108 if (hostsig == SIGBUS) return TARGET_SIGNAL_BUS;
109#endif
110#if defined (SIGSEGV)
111 if (hostsig == SIGSEGV) return TARGET_SIGNAL_SEGV;
112#endif
113#if defined (SIGSYS)
114 if (hostsig == SIGSYS) return TARGET_SIGNAL_SYS;
115#endif
116#if defined (SIGPIPE)
117 if (hostsig == SIGPIPE) return TARGET_SIGNAL_PIPE;
118#endif
119#if defined (SIGALRM)
120 if (hostsig == SIGALRM) return TARGET_SIGNAL_ALRM;
121#endif
122#if defined (SIGTERM)
123 if (hostsig == SIGTERM) return TARGET_SIGNAL_TERM;
124#endif
125#if defined (SIGUSR1)
126 if (hostsig == SIGUSR1) return TARGET_SIGNAL_USR1;
127#endif
128#if defined (SIGUSR2)
129 if (hostsig == SIGUSR2) return TARGET_SIGNAL_USR2;
130#endif
131#if defined (SIGCLD)
132 if (hostsig == SIGCLD) return TARGET_SIGNAL_CHLD;
133#endif
134#if defined (SIGCHLD)
135 if (hostsig == SIGCHLD) return TARGET_SIGNAL_CHLD;
136#endif
137#if defined (SIGPWR)
138 if (hostsig == SIGPWR) return TARGET_SIGNAL_PWR;
139#endif
140#if defined (SIGWINCH)
141 if (hostsig == SIGWINCH) return TARGET_SIGNAL_WINCH;
142#endif
143#if defined (SIGURG)
144 if (hostsig == SIGURG) return TARGET_SIGNAL_URG;
145#endif
146#if defined (SIGIO)
147 if (hostsig == SIGIO) return TARGET_SIGNAL_IO;
148#endif
149#if defined (SIGPOLL)
150 if (hostsig == SIGPOLL) return TARGET_SIGNAL_POLL;
151#endif
152#if defined (SIGSTOP)
153 if (hostsig == SIGSTOP) return TARGET_SIGNAL_STOP;
154#endif
155#if defined (SIGTSTP)
156 if (hostsig == SIGTSTP) return TARGET_SIGNAL_TSTP;
157#endif
158#if defined (SIGCONT)
159 if (hostsig == SIGCONT) return TARGET_SIGNAL_CONT;
160#endif
161#if defined (SIGTTIN)
162 if (hostsig == SIGTTIN) return TARGET_SIGNAL_TTIN;
163#endif
164#if defined (SIGTTOU)
165 if (hostsig == SIGTTOU) return TARGET_SIGNAL_TTOU;
166#endif
167#if defined (SIGVTALRM)
168 if (hostsig == SIGVTALRM) return TARGET_SIGNAL_VTALRM;
169#endif
170#if defined (SIGPROF)
171 if (hostsig == SIGPROF) return TARGET_SIGNAL_PROF;
172#endif
173#if defined (SIGXCPU)
174 if (hostsig == SIGXCPU) return TARGET_SIGNAL_XCPU;
175#endif
176#if defined (SIGXFSZ)
177 if (hostsig == SIGXFSZ) return TARGET_SIGNAL_XFSZ;
178#endif
179#if defined (SIGWIND)
180 if (hostsig == SIGWIND) return TARGET_SIGNAL_WIND;
181#endif
182#if defined (SIGPHONE)
183 if (hostsig == SIGPHONE) return TARGET_SIGNAL_PHONE;
184#endif
185#if defined (SIGLOST)
186 if (hostsig == SIGLOST) return TARGET_SIGNAL_LOST;
187#endif
188#if defined (SIGWAITING)
189 if (hostsig == SIGWAITING) return TARGET_SIGNAL_WAITING;
190#endif
191#if defined (SIGLWP)
192 if (hostsig == SIGLWP) return TARGET_SIGNAL_LWP;
193#endif
194#if defined (SIGDANGER)
195 if (hostsig == SIGDANGER) return TARGET_SIGNAL_DANGER;
196#endif
197#if defined (SIGGRANT)
198 if (hostsig == SIGGRANT) return TARGET_SIGNAL_GRANT;
199#endif
200#if defined (SIGRETRACT)
201 if (hostsig == SIGRETRACT) return TARGET_SIGNAL_RETRACT;
202#endif
203#if defined (SIGMSG)
204 if (hostsig == SIGMSG) return TARGET_SIGNAL_MSG;
205#endif
206#if defined (SIGSOUND)
207 if (hostsig == SIGSOUND) return TARGET_SIGNAL_SOUND;
208#endif
209#if defined (SIGSAK)
210 if (hostsig == SIGSAK) return TARGET_SIGNAL_SAK;
211#endif
212 return TARGET_SIGNAL_UNKNOWN;
213}
214
215int
216target_signal_to_host (oursig)
217 enum target_signal oursig;
218{
219 switch (oursig)
220 {
221 case TARGET_SIGNAL_0: return 0;
222
223#if defined (SIGHUP)
224 case TARGET_SIGNAL_HUP: return SIGHUP;
225#endif
226#if defined (SIGINT)
227 case TARGET_SIGNAL_INT: return SIGINT;
228#endif
229#if defined (SIGQUIT)
230 case TARGET_SIGNAL_QUIT: return SIGQUIT;
231#endif
232#if defined (SIGILL)
233 case TARGET_SIGNAL_ILL: return SIGILL;
234#endif
235#if defined (SIGTRAP)
236 case TARGET_SIGNAL_TRAP: return SIGTRAP;
237#endif
238#if defined (SIGABRT)
239 case TARGET_SIGNAL_ABRT: return SIGABRT;
240#endif
241#if defined (SIGEMT)
242 case TARGET_SIGNAL_EMT: return SIGEMT;
243#endif
244#if defined (SIGFPE)
245 case TARGET_SIGNAL_FPE: return SIGFPE;
246#endif
247#if defined (SIGKILL)
248 case TARGET_SIGNAL_KILL: return SIGKILL;
249#endif
250#if defined (SIGBUS)
251 case TARGET_SIGNAL_BUS: return SIGBUS;
252#endif
253#if defined (SIGSEGV)
254 case TARGET_SIGNAL_SEGV: return SIGSEGV;
255#endif
256#if defined (SIGSYS)
257 case TARGET_SIGNAL_SYS: return SIGSYS;
258#endif
259#if defined (SIGPIPE)
260 case TARGET_SIGNAL_PIPE: return SIGPIPE;
261#endif
262#if defined (SIGALRM)
263 case TARGET_SIGNAL_ALRM: return SIGALRM;
264#endif
265#if defined (SIGTERM)
266 case TARGET_SIGNAL_TERM: return SIGTERM;
267#endif
268#if defined (SIGUSR1)
269 case TARGET_SIGNAL_USR1: return SIGUSR1;
270#endif
271#if defined (SIGUSR2)
272 case TARGET_SIGNAL_USR2: return SIGUSR2;
273#endif
274#if defined (SIGCHLD) || defined (SIGCLD)
275 case TARGET_SIGNAL_CHLD:
276#if defined (SIGCHLD)
277 return SIGCHLD;
278#else
279 return SIGCLD;
280#endif
281#endif /* SIGCLD or SIGCHLD */
282#if defined (SIGPWR)
283 case TARGET_SIGNAL_PWR: return SIGPWR;
284#endif
285#if defined (SIGWINCH)
286 case TARGET_SIGNAL_WINCH: return SIGWINCH;
287#endif
288#if defined (SIGURG)
289 case TARGET_SIGNAL_URG: return SIGURG;
290#endif
291#if defined (SIGIO)
292 case TARGET_SIGNAL_IO: return SIGIO;
293#endif
294#if defined (SIGPOLL)
295 case TARGET_SIGNAL_POLL: return SIGPOLL;
296#endif
297#if defined (SIGSTOP)
298 case TARGET_SIGNAL_STOP: return SIGSTOP;
299#endif
300#if defined (SIGTSTP)
301 case TARGET_SIGNAL_TSTP: return SIGTSTP;
302#endif
303#if defined (SIGCONT)
304 case TARGET_SIGNAL_CONT: return SIGCONT;
305#endif
306#if defined (SIGTTIN)
307 case TARGET_SIGNAL_TTIN: return SIGTTIN;
308#endif
309#if defined (SIGTTOU)
310 case TARGET_SIGNAL_TTOU: return SIGTTOU;
311#endif
312#if defined (SIGVTALRM)
313 case TARGET_SIGNAL_VTALRM: return SIGVTALRM;
314#endif
315#if defined (SIGPROF)
316 case TARGET_SIGNAL_PROF: return SIGPROF;
317#endif
318#if defined (SIGXCPU)
319 case TARGET_SIGNAL_XCPU: return SIGXCPU;
320#endif
321#if defined (SIGXFSZ)
322 case TARGET_SIGNAL_XFSZ: return SIGXFSZ;
323#endif
324#if defined (SIGWIND)
325 case TARGET_SIGNAL_WIND: return SIGWIND;
326#endif
327#if defined (SIGPHONE)
328 case TARGET_SIGNAL_PHONE: return SIGPHONE;
329#endif
330#if defined (SIGLOST)
331 case TARGET_SIGNAL_LOST: return SIGLOST;
332#endif
333#if defined (SIGWAITING)
334 case TARGET_SIGNAL_WAITING: return SIGWAITING;
335#endif
336#if defined (SIGLWP)
337 case TARGET_SIGNAL_LWP: return SIGLWP;
338#endif
339#if defined (SIGDANGER)
340 case TARGET_SIGNAL_DANGER: return SIGDANGER;
341#endif
342#if defined (SIGGRANT)
343 case TARGET_SIGNAL_GRANT: return SIGGRANT;
344#endif
345#if defined (SIGRETRACT)
346 case TARGET_SIGNAL_RETRACT: return SIGRETRACT;
347#endif
348#if defined (SIGMSG)
349 case TARGET_SIGNAL_MSG: return SIGMSG;
350#endif
351#if defined (SIGSOUND)
352 case TARGET_SIGNAL_SOUND: return SIGSOUND;
353#endif
354#if defined (SIGSAK)
355 case TARGET_SIGNAL_SAK: return SIGSAK;
356#endif
357 default:
358 /* The user might be trying to do "signal SIGSAK" where this system
359 doesn't have SIGSAK. */
360 warning ("Signal %s does not exist on this system.\n",
361 target_signal_to_name (oursig));
362 return 0;
363 }
364}
365
366/* Helper function for child_wait and the Lynx derivatives of child_wait.
367 HOSTSTATUS is the waitstatus from wait() or the equivalent; store our
368 translation of that in OURSTATUS. */
369void
370store_waitstatus (ourstatus, hoststatus)
371 struct target_waitstatus *ourstatus;
372 int hoststatus;
373{
374 if (WIFEXITED (hoststatus))
375 {
376 ourstatus->kind = TARGET_WAITKIND_EXITED;
377 ourstatus->value.integer = WEXITSTATUS (hoststatus);
378 }
379 else if (!WIFSTOPPED (hoststatus))
380 {
381 ourstatus->kind = TARGET_WAITKIND_SIGNALLED;
382 ourstatus->value.sig = target_signal_from_host (WTERMSIG (hoststatus));
383 }
384 else
385 {
386 ourstatus->kind = TARGET_WAITKIND_STOPPED;
387 ourstatus->value.sig = target_signal_from_host (WSTOPSIG (hoststatus));
388 }
389}
390
de43d7d0
SG
391#ifndef CHILD_WAIT
392
bd5635a1 393/* Wait for child to do something. Return pid of child, or -1 in case
67ac9759 394 of error; store status through argument pointer OURSTATUS. */
bd5635a1 395
dcc8abce 396static int
67ac9759 397child_wait (pid, ourstatus)
de43d7d0 398 int pid;
67ac9759 399 struct target_waitstatus *ourstatus;
bd5635a1 400{
de43d7d0 401 int save_errno;
67ac9759 402 int status;
bd5635a1
RP
403
404 do {
de43d7d0
SG
405 if (attach_flag)
406 set_sigint_trap(); /* Causes SIGINT to be passed on to the
407 attached process. */
67ac9759 408 pid = wait (&status);
de43d7d0
SG
409 save_errno = errno;
410
411 if (attach_flag)
412 clear_sigint_trap();
413
414 if (pid == -1)
bd5635a1 415 {
de43d7d0
SG
416 if (save_errno == EINTR)
417 continue;
67ac9759 418 fprintf_unfiltered (gdb_stderr, "Child process unexpectedly missing: %s.\n",
de43d7d0 419 safe_strerror (save_errno));
67ac9759
JK
420 /* Claim it exited with unknown signal. */
421 ourstatus->kind = TARGET_WAITKIND_SIGNALLED;
422 ourstatus->value.sig = TARGET_SIGNAL_UNKNOWN;
bd5635a1
RP
423 return -1;
424 }
425 } while (pid != inferior_pid); /* Some other child died or stopped */
67ac9759 426 store_waitstatus (ourstatus, status);
bd5635a1
RP
427 return pid;
428}
de43d7d0 429#endif /* CHILD_WAIT */
bd5635a1 430
836e343b 431/* Attach to process PID, then initialize for debugging it. */
310cc570
RP
432
433static void
434child_attach (args, from_tty)
435 char *args;
436 int from_tty;
437{
310cc570
RP
438 if (!args)
439 error_no_arg ("process-id to attach");
440
441#ifndef ATTACH_DETACH
442 error ("Can't attach to a process on this machine.");
443#else
100f92e2
JK
444 {
445 char *exec_file;
446 int pid;
310cc570 447
100f92e2 448 pid = atoi (args);
310cc570 449
100f92e2
JK
450 if (pid == getpid()) /* Trying to masturbate? */
451 error ("I refuse to debug myself!");
310cc570 452
100f92e2
JK
453 if (from_tty)
454 {
455 exec_file = (char *) get_exec_file (0);
310cc570 456
100f92e2 457 if (exec_file)
67ac9759 458 printf_unfiltered ("Attaching to program `%s', %s\n", exec_file,
100f92e2
JK
459 target_pid_to_str (pid));
460 else
67ac9759 461 printf_unfiltered ("Attaching to %s\n", target_pid_to_str (pid));
100f92e2 462
67ac9759 463 gdb_flush (gdb_stdout);
100f92e2 464 }
310cc570 465
100f92e2
JK
466 attach (pid);
467 inferior_pid = pid;
468 push_target (&child_ops);
469 }
310cc570
RP
470#endif /* ATTACH_DETACH */
471}
472
3aa6856a
JG
473
474/* Take a program previously attached to and detaches it.
475 The program resumes execution and will no longer stop
476 on signals, etc. We'd better not have left any breakpoints
477 in the program or it'll die when it hits one. For this
478 to work, it may be necessary for the process to have been
479 previously attached. It *might* work if the program was
480 started via the normal ptrace (PTRACE_TRACEME). */
bd5635a1
RP
481
482static void
483child_detach (args, from_tty)
484 char *args;
485 int from_tty;
486{
bd5635a1 487#ifdef ATTACH_DETACH
100f92e2
JK
488 {
489 int siggnal = 0;
490
491 if (from_tty)
492 {
493 char *exec_file = get_exec_file (0);
494 if (exec_file == 0)
495 exec_file = "";
67ac9759 496 printf_unfiltered ("Detaching from program: %s %s\n", exec_file,
100f92e2 497 target_pid_to_str (inferior_pid));
67ac9759 498 gdb_flush (gdb_stdout);
100f92e2
JK
499 }
500 if (args)
501 siggnal = atoi (args);
502
503 detach (siggnal);
504 inferior_pid = 0;
505 unpush_target (&child_ops);
506 }
bd5635a1 507#else
100f92e2 508 error ("This version of Unix does not support detaching a process.");
bd5635a1
RP
509#endif
510}
511
512/* Get ready to modify the registers array. On machines which store
513 individual registers, this doesn't need to do anything. On machines
514 which store all the registers in one fell swoop, this makes sure
515 that registers contains all the registers from the program being
516 debugged. */
517
dcc8abce 518static void
bd5635a1
RP
519child_prepare_to_store ()
520{
521#ifdef CHILD_PREPARE_TO_STORE
522 CHILD_PREPARE_TO_STORE ();
523#endif
524}
525
bd5635a1
RP
526/* Print status information about what we're accessing. */
527
528static void
dcc8abce
JG
529child_files_info (ignore)
530 struct target_ops *ignore;
bd5635a1 531{
67ac9759 532 printf_unfiltered ("\tUsing the running image of %s %s.\n",
de43d7d0 533 attach_flag? "attached": "child", target_pid_to_str (inferior_pid));
bd5635a1
RP
534}
535
e1ce8aa5 536/* ARGSUSED */
70dcc196
JK
537static void
538child_open (arg, from_tty)
539 char *arg;
540 int from_tty;
541{
542 error ("Use the \"run\" command to start a Unix child process.");
543}
544
de43d7d0
SG
545/* Stub function which causes the inferior that runs it, to be ptrace-able
546 by its parent process. */
547
548static void
549ptrace_me ()
550{
551 /* "Trace me, Dr. Memory!" */
552 call_ptrace (0, 0, (PTRACE_ARG3_TYPE) 0, 0);
553}
554
555/* Stub function which causes the GDB that runs it, to start ptrace-ing
556 the child process. */
557
558static void
559ptrace_him (pid)
560 int pid;
561{
562 push_target (&child_ops);
67ac9759
JK
563
564#ifdef START_INFERIOR_TRAPS_EXPECTED
565 startup_inferior (START_INFERIOR_TRAPS_EXPECTED);
566#else
567 /* One trap to exec the shell, one to exec the program being debugged. */
568 startup_inferior (2);
569#endif
de43d7d0
SG
570}
571
310cc570
RP
572/* Start an inferior Unix child process and sets inferior_pid to its pid.
573 EXEC_FILE is the file to run.
574 ALLARGS is a string containing the arguments to the program.
575 ENV is the environment vector to pass. Errors reported with error(). */
576
310cc570
RP
577static void
578child_create_inferior (exec_file, allargs, env)
579 char *exec_file;
580 char *allargs;
581 char **env;
582{
de43d7d0
SG
583 fork_inferior (exec_file, allargs, env, ptrace_me, ptrace_him);
584 /* We are at the first instruction we care about. */
585 /* Pedal to the metal... */
67ac9759 586 proceed ((CORE_ADDR) -1, TARGET_SIGNAL_0, 0);
310cc570
RP
587}
588
589static void
590child_mourn_inferior ()
591{
592 unpush_target (&child_ops);
593 generic_mourn_inferior ();
594}
595
596static int
597child_can_run ()
598{
599 return(1);
600}
3aa6856a 601\f
bd5635a1 602struct target_ops child_ops = {
dcc8abce
JG
603 "child", /* to_shortname */
604 "Unix child process", /* to_longname */
605 "Unix child process (started by the \"run\" command).", /* to_doc */
606 child_open, /* to_open */
607 0, /* to_close */
608 child_attach, /* to_attach */
609 child_detach, /* to_detach */
610 child_resume, /* to_resume */
611 child_wait, /* to_wait */
612 fetch_inferior_registers, /* to_fetch_registers */
613 store_inferior_registers, /* to_store_registers */
614 child_prepare_to_store, /* to_prepare_to_store */
615 child_xfer_memory, /* to_xfer_memory */
616 child_files_info, /* to_files_info */
617 memory_insert_breakpoint, /* to_insert_breakpoint */
618 memory_remove_breakpoint, /* to_remove_breakpoint */
619 terminal_init_inferior, /* to_terminal_init */
620 terminal_inferior, /* to_terminal_inferior */
621 terminal_ours_for_output, /* to_terminal_ours_for_output */
622 terminal_ours, /* to_terminal_ours */
623 child_terminal_info, /* to_terminal_info */
624 kill_inferior, /* to_kill */
625 0, /* to_load */
626 0, /* to_lookup_symbol */
627 child_create_inferior, /* to_create_inferior */
628 child_mourn_inferior, /* to_mourn_inferior */
310cc570 629 child_can_run, /* to_can_run */
de43d7d0 630 0, /* to_notice_signals */
dcc8abce
JG
631 process_stratum, /* to_stratum */
632 0, /* to_next */
633 1, /* to_has_all_memory */
634 1, /* to_has_memory */
635 1, /* to_has_stack */
636 1, /* to_has_registers */
637 1, /* to_has_execution */
638 0, /* sections */
639 0, /* sections_end */
640 OPS_MAGIC /* to_magic */
bd5635a1
RP
641};
642
643void
644_initialize_inftarg ()
645{
646 add_target (&child_ops);
647}
This page took 0.159907 seconds and 4 git commands to generate.