Add basic event handling in the NetBSD target
[deliverable/binutils-gdb.git] / gdb / nbsd-nat.c
1 /* Native-dependent code for NetBSD.
2
3 Copyright (C) 2006-2020 Free Software Foundation, Inc.
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
19
20 #include "defs.h"
21
22 #include "nbsd-nat.h"
23 #include "gdbthread.h"
24 #include "nbsd-tdep.h"
25 #include "inferior.h"
26 #include "gdbarch.h"
27
28 #include <sys/types.h>
29 #include <sys/ptrace.h>
30 #include <sys/sysctl.h>
31 #include <sys/wait.h>
32
33 /* Return the name of a file that can be opened to get the symbols for
34 the child process identified by PID. */
35
36 char *
37 nbsd_nat_target::pid_to_exec_file (int pid)
38 {
39 static char buf[PATH_MAX];
40 size_t buflen;
41 int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_PATHNAME};
42 buflen = sizeof (buf);
43 if (sysctl (mib, ARRAY_SIZE (mib), buf, &buflen, NULL, 0))
44 return NULL;
45 return buf;
46 }
47
48 /* Return the current directory for the process identified by PID. */
49
50 static std::string
51 nbsd_pid_to_cwd (int pid)
52 {
53 char buf[PATH_MAX];
54 size_t buflen;
55 int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_CWD};
56 buflen = sizeof (buf);
57 if (sysctl (mib, ARRAY_SIZE (mib), buf, &buflen, NULL, 0))
58 return "";
59 return buf;
60 }
61
62 /* Return the kinfo_proc2 structure for the process identified by PID. */
63
64 static bool
65 nbsd_pid_to_kinfo_proc2 (pid_t pid, struct kinfo_proc2 *kp)
66 {
67 gdb_assert (kp != nullptr);
68
69 size_t size = sizeof (*kp);
70 int mib[6] = {CTL_KERN, KERN_PROC2, KERN_PROC_PID, pid,
71 static_cast<int> (size), 1};
72 return !sysctl (mib, ARRAY_SIZE (mib), kp, &size, NULL, 0);
73 }
74
75 /* Return the command line for the process identified by PID. */
76
77 static gdb::unique_xmalloc_ptr<char[]>
78 nbsd_pid_to_cmdline (int pid)
79 {
80 int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_ARGV};
81
82 size_t size = 0;
83 if (sysctl (mib, ARRAY_SIZE (mib), NULL, &size, NULL, 0) == -1 || size == 0)
84 return nullptr;
85
86 gdb::unique_xmalloc_ptr<char[]> args (XNEWVAR (char, size));
87
88 if (sysctl (mib, ARRAY_SIZE (mib), args.get (), &size, NULL, 0) == -1
89 || size == 0)
90 return nullptr;
91
92 /* Arguments are returned as a flattened string with NUL separators.
93 Join the arguments with spaces to form a single string. */
94 for (size_t i = 0; i < size - 1; i++)
95 if (args[i] == '\0')
96 args[i] = ' ';
97 args[size - 1] = '\0';
98
99 return args;
100 }
101
102 /* Generic thread (LWP) lister within a specified process. The callback
103 parameters is a C++ function that is called for each detected thread. */
104
105 static bool
106 nbsd_thread_lister (const pid_t pid,
107 gdb::function_view<bool (const struct kinfo_lwp *)>
108 callback)
109 {
110 int mib[5] = {CTL_KERN, KERN_LWP, pid, sizeof (struct kinfo_lwp), 0};
111 size_t size;
112
113 if (sysctl (mib, ARRAY_SIZE (mib), NULL, &size, NULL, 0) == -1 || size == 0)
114 perror_with_name (("sysctl"));
115
116 mib[4] = size / sizeof (size_t);
117
118 gdb::unique_xmalloc_ptr<struct kinfo_lwp[]> kl
119 ((struct kinfo_lwp *) xcalloc (size, 1));
120
121 if (sysctl (mib, ARRAY_SIZE (mib), kl.get (), &size, NULL, 0) == -1
122 || size == 0)
123 perror_with_name (("sysctl"));
124
125 for (size_t i = 0; i < size / sizeof (struct kinfo_lwp); i++)
126 {
127 struct kinfo_lwp *l = &kl[i];
128
129 /* Return true if the specified thread is alive. */
130 auto lwp_alive
131 = [] (struct kinfo_lwp *lwp)
132 {
133 switch (lwp->l_stat)
134 {
135 case LSSLEEP:
136 case LSRUN:
137 case LSONPROC:
138 case LSSTOP:
139 case LSSUSPENDED:
140 return true;
141 default:
142 return false;
143 }
144 };
145
146 /* Ignore embryonic or demised threads. */
147 if (!lwp_alive (l))
148 continue;
149
150 if (callback (l))
151 return true;
152 }
153
154 return false;
155 }
156
157 /* Return true if PTID is still active in the inferior. */
158
159 bool
160 nbsd_nat_target::thread_alive (ptid_t ptid)
161 {
162 pid_t pid = ptid.pid ();
163 int lwp = ptid.lwp ();
164
165 auto fn
166 = [&lwp] (const struct kinfo_lwp *kl)
167 {
168 return kl->l_lid == lwp;
169 };
170
171 return nbsd_thread_lister (pid, fn);
172 }
173
174 /* Return the name assigned to a thread by an application. Returns
175 the string in a static buffer. */
176
177 const char *
178 nbsd_nat_target::thread_name (struct thread_info *thr)
179 {
180 ptid_t ptid = thr->ptid;
181 pid_t pid = ptid.pid ();
182 int lwp = ptid.lwp ();
183
184 static char buf[KI_LNAMELEN] = {};
185
186 auto fn
187 = [&lwp] (const struct kinfo_lwp *kl)
188 {
189 if (kl->l_lid == lwp)
190 {
191 xsnprintf (buf, sizeof buf, "%s", kl->l_name);
192 return true;
193 }
194 return false;
195 };
196
197 if (nbsd_thread_lister (pid, fn))
198 return buf;
199 else
200 return NULL;
201 }
202
203 /* Implement the "post_attach" target_ops method. */
204
205 static void
206 nbsd_add_threads (nbsd_nat_target *target, pid_t pid)
207 {
208 auto fn
209 = [&target, &pid] (const struct kinfo_lwp *kl)
210 {
211 ptid_t ptid = ptid_t (pid, kl->l_lid, 0);
212 if (!in_thread_list (target, ptid))
213 {
214 if (inferior_ptid.lwp () == 0)
215 thread_change_ptid (target, inferior_ptid, ptid);
216 else
217 add_thread (target, ptid);
218 }
219 return false;
220 };
221
222 nbsd_thread_lister (pid, fn);
223 }
224
225 /* Implement the "post_attach" target_ops method. */
226
227 void
228 nbsd_nat_target::post_attach (int pid)
229 {
230 nbsd_add_threads (this, pid);
231 }
232
233 /* Implement the "update_thread_list" target_ops method. */
234
235 void
236 nbsd_nat_target::update_thread_list ()
237 {
238 prune_threads ();
239
240 nbsd_add_threads (this, inferior_ptid.pid ());
241 }
242
243 /* Convert PTID to a string. */
244
245 std::string
246 nbsd_nat_target::pid_to_str (ptid_t ptid)
247 {
248 int lwp = ptid.lwp ();
249
250 if (lwp != 0)
251 {
252 pid_t pid = ptid.pid ();
253
254 return string_printf ("LWP %d of process %d", lwp, pid);
255 }
256
257 return normal_pid_to_str (ptid);
258 }
259
260 /* Retrieve all the memory regions in the specified process. */
261
262 static gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]>
263 nbsd_kinfo_get_vmmap (pid_t pid, size_t *size)
264 {
265 int mib[5] = {CTL_VM, VM_PROC, VM_PROC_MAP, pid,
266 sizeof (struct kinfo_vmentry)};
267
268 size_t length = 0;
269 if (sysctl (mib, ARRAY_SIZE (mib), NULL, &length, NULL, 0))
270 {
271 *size = 0;
272 return NULL;
273 }
274
275 /* Prereserve more space. The length argument is volatile and can change
276 between the sysctl(3) calls as this function can be called against a
277 running process. */
278 length = length * 5 / 3;
279
280 gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]> kiv
281 (XNEWVAR (kinfo_vmentry, length));
282
283 if (sysctl (mib, ARRAY_SIZE (mib), kiv.get (), &length, NULL, 0))
284 {
285 *size = 0;
286 return NULL;
287 }
288
289 *size = length / sizeof (struct kinfo_vmentry);
290 return kiv;
291 }
292
293 /* Iterate over all the memory regions in the current inferior,
294 calling FUNC for each memory region. OBFD is passed as the last
295 argument to FUNC. */
296
297 int
298 nbsd_nat_target::find_memory_regions (find_memory_region_ftype func,
299 void *data)
300 {
301 pid_t pid = inferior_ptid.pid ();
302
303 size_t nitems;
304 gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]> vmentl
305 = nbsd_kinfo_get_vmmap (pid, &nitems);
306 if (vmentl == NULL)
307 perror_with_name (_("Couldn't fetch VM map entries."));
308
309 for (size_t i = 0; i < nitems; i++)
310 {
311 struct kinfo_vmentry *kve = &vmentl[i];
312
313 /* Skip unreadable segments and those where MAP_NOCORE has been set. */
314 if (!(kve->kve_protection & KVME_PROT_READ)
315 || kve->kve_flags & KVME_FLAG_NOCOREDUMP)
316 continue;
317
318 /* Skip segments with an invalid type. */
319 switch (kve->kve_type)
320 {
321 case KVME_TYPE_VNODE:
322 case KVME_TYPE_ANON:
323 case KVME_TYPE_SUBMAP:
324 case KVME_TYPE_OBJECT:
325 break;
326 default:
327 continue;
328 }
329
330 size_t size = kve->kve_end - kve->kve_start;
331 if (info_verbose)
332 {
333 fprintf_filtered (gdb_stdout,
334 "Save segment, %ld bytes at %s (%c%c%c)\n",
335 (long) size,
336 paddress (target_gdbarch (), kve->kve_start),
337 kve->kve_protection & KVME_PROT_READ ? 'r' : '-',
338 kve->kve_protection & KVME_PROT_WRITE ? 'w' : '-',
339 kve->kve_protection & KVME_PROT_EXEC ? 'x' : '-');
340 }
341
342 /* Invoke the callback function to create the corefile segment.
343 Pass MODIFIED as true, we do not know the real modification state. */
344 func (kve->kve_start, size, kve->kve_protection & KVME_PROT_READ,
345 kve->kve_protection & KVME_PROT_WRITE,
346 kve->kve_protection & KVME_PROT_EXEC, 1, data);
347 }
348 return 0;
349 }
350
351 /* Implement the "info_proc" target_ops method. */
352
353 bool
354 nbsd_nat_target::info_proc (const char *args, enum info_proc_what what)
355 {
356 pid_t pid;
357 bool do_cmdline = false;
358 bool do_cwd = false;
359 bool do_exe = false;
360 bool do_mappings = false;
361 bool do_status = false;
362
363 switch (what)
364 {
365 case IP_MINIMAL:
366 do_cmdline = true;
367 do_cwd = true;
368 do_exe = true;
369 break;
370 case IP_STAT:
371 case IP_STATUS:
372 do_status = true;
373 break;
374 case IP_MAPPINGS:
375 do_mappings = true;
376 break;
377 case IP_CMDLINE:
378 do_cmdline = true;
379 break;
380 case IP_EXE:
381 do_exe = true;
382 break;
383 case IP_CWD:
384 do_cwd = true;
385 break;
386 case IP_ALL:
387 do_cmdline = true;
388 do_cwd = true;
389 do_exe = true;
390 do_mappings = true;
391 do_status = true;
392 break;
393 default:
394 error (_("Not supported on this target."));
395 }
396
397 gdb_argv built_argv (args);
398 if (built_argv.count () == 0)
399 {
400 pid = inferior_ptid.pid ();
401 if (pid == 0)
402 error (_("No current process: you must name one."));
403 }
404 else if (built_argv.count () == 1 && isdigit (built_argv[0][0]))
405 pid = strtol (built_argv[0], NULL, 10);
406 else
407 error (_("Invalid arguments."));
408
409 printf_filtered (_("process %d\n"), pid);
410
411 if (do_cmdline)
412 {
413 gdb::unique_xmalloc_ptr<char[]> cmdline = nbsd_pid_to_cmdline (pid);
414 if (cmdline != nullptr)
415 printf_filtered ("cmdline = '%s'\n", cmdline.get ());
416 else
417 warning (_("unable to fetch command line"));
418 }
419 if (do_cwd)
420 {
421 std::string cwd = nbsd_pid_to_cwd (pid);
422 if (cwd != "")
423 printf_filtered ("cwd = '%s'\n", cwd.c_str ());
424 else
425 warning (_("unable to fetch current working directory"));
426 }
427 if (do_exe)
428 {
429 const char *exe = pid_to_exec_file (pid);
430 if (exe != nullptr)
431 printf_filtered ("exe = '%s'\n", exe);
432 else
433 warning (_("unable to fetch executable path name"));
434 }
435 if (do_mappings)
436 {
437 size_t nvment;
438 gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]> vmentl
439 = nbsd_kinfo_get_vmmap (pid, &nvment);
440
441 if (vmentl != nullptr)
442 {
443 int addr_bit = TARGET_CHAR_BIT * sizeof (void *);
444 nbsd_info_proc_mappings_header (addr_bit);
445
446 struct kinfo_vmentry *kve = vmentl.get ();
447 for (int i = 0; i < nvment; i++, kve++)
448 nbsd_info_proc_mappings_entry (addr_bit, kve->kve_start,
449 kve->kve_end, kve->kve_offset,
450 kve->kve_flags, kve->kve_protection,
451 kve->kve_path);
452 }
453 else
454 warning (_("unable to fetch virtual memory map"));
455 }
456 if (do_status)
457 {
458 struct kinfo_proc2 kp;
459 if (!nbsd_pid_to_kinfo_proc2 (pid, &kp))
460 warning (_("Failed to fetch process information"));
461 else
462 {
463 auto process_status
464 = [] (int8_t stat)
465 {
466 switch (stat)
467 {
468 case SIDL:
469 return "IDL";
470 case SACTIVE:
471 return "ACTIVE";
472 case SDYING:
473 return "DYING";
474 case SSTOP:
475 return "STOP";
476 case SZOMB:
477 return "ZOMB";
478 case SDEAD:
479 return "DEAD";
480 default:
481 return "? (unknown)";
482 }
483 };
484
485 printf_filtered ("Name: %s\n", kp.p_comm);
486 printf_filtered ("State: %s\n", process_status(kp.p_realstat));
487 printf_filtered ("Parent process: %" PRId32 "\n", kp.p_ppid);
488 printf_filtered ("Process group: %" PRId32 "\n", kp.p__pgid);
489 printf_filtered ("Session id: %" PRId32 "\n", kp.p_sid);
490 printf_filtered ("TTY: %" PRId32 "\n", kp.p_tdev);
491 printf_filtered ("TTY owner process group: %" PRId32 "\n", kp.p_tpgid);
492 printf_filtered ("User IDs (real, effective, saved): "
493 "%" PRIu32 " %" PRIu32 " %" PRIu32 "\n",
494 kp.p_ruid, kp.p_uid, kp.p_svuid);
495 printf_filtered ("Group IDs (real, effective, saved): "
496 "%" PRIu32 " %" PRIu32 " %" PRIu32 "\n",
497 kp.p_rgid, kp.p_gid, kp.p_svgid);
498
499 printf_filtered ("Groups:");
500 for (int i = 0; i < kp.p_ngroups; i++)
501 printf_filtered (" %" PRIu32, kp.p_groups[i]);
502 printf_filtered ("\n");
503 printf_filtered ("Minor faults (no memory page): %" PRIu64 "\n",
504 kp.p_uru_minflt);
505 printf_filtered ("Major faults (memory page faults): %" PRIu64 "\n",
506 kp.p_uru_majflt);
507 printf_filtered ("utime: %" PRIu32 ".%06" PRIu32 "\n",
508 kp.p_uutime_sec, kp.p_uutime_usec);
509 printf_filtered ("stime: %" PRIu32 ".%06" PRIu32 "\n",
510 kp.p_ustime_sec, kp.p_ustime_usec);
511 printf_filtered ("utime+stime, children: %" PRIu32 ".%06" PRIu32 "\n",
512 kp.p_uctime_sec, kp.p_uctime_usec);
513 printf_filtered ("'nice' value: %" PRIu8 "\n", kp.p_nice);
514 printf_filtered ("Start time: %" PRIu32 ".%06" PRIu32 "\n",
515 kp.p_ustart_sec, kp.p_ustart_usec);
516 int pgtok = getpagesize () / 1024;
517 printf_filtered ("Data size: %" PRIuMAX " kB\n",
518 (uintmax_t) kp.p_vm_dsize * pgtok);
519 printf_filtered ("Stack size: %" PRIuMAX " kB\n",
520 (uintmax_t) kp.p_vm_ssize * pgtok);
521 printf_filtered ("Text size: %" PRIuMAX " kB\n",
522 (uintmax_t) kp.p_vm_tsize * pgtok);
523 printf_filtered ("Resident set size: %" PRIuMAX " kB\n",
524 (uintmax_t) kp.p_vm_rssize * pgtok);
525 printf_filtered ("Maximum RSS: %" PRIu64 " kB\n", kp.p_uru_maxrss);
526 printf_filtered ("Pending Signals:");
527 for (size_t i = 0; i < ARRAY_SIZE (kp.p_siglist.__bits); i++)
528 printf_filtered (" %08" PRIx32, kp.p_siglist.__bits[i]);
529 printf_filtered ("\n");
530 printf_filtered ("Ignored Signals:");
531 for (size_t i = 0; i < ARRAY_SIZE (kp.p_sigignore.__bits); i++)
532 printf_filtered (" %08" PRIx32, kp.p_sigignore.__bits[i]);
533 printf_filtered ("\n");
534 printf_filtered ("Caught Signals:");
535 for (size_t i = 0; i < ARRAY_SIZE (kp.p_sigcatch.__bits); i++)
536 printf_filtered (" %08" PRIx32, kp.p_sigcatch.__bits[i]);
537 printf_filtered ("\n");
538 }
539 }
540
541 return true;
542 }
543
544 /* Resume execution of a specified PTID, that points to a process or a thread
545 within a process. If one thread is specified, all other threads are
546 suspended. If STEP is nonzero, single-step it. If SIGNAL is nonzero,
547 give it that signal. */
548
549 static void
550 nbsd_resume(nbsd_nat_target *target, ptid_t ptid, int step,
551 enum gdb_signal signal)
552 {
553 int request;
554
555 gdb_assert (minus_one_ptid != ptid);
556
557 if (ptid.lwp_p ())
558 {
559 /* If ptid is a specific LWP, suspend all other LWPs in the process. */
560 inferior *inf = find_inferior_ptid (target, ptid);
561
562 for (thread_info *tp : inf->non_exited_threads ())
563 {
564 if (tp->ptid.lwp () == ptid.lwp ())
565 request = PT_RESUME;
566 else
567 request = PT_SUSPEND;
568
569 if (ptrace (request, tp->ptid.pid (), NULL, tp->ptid.lwp ()) == -1)
570 perror_with_name (("ptrace"));
571 }
572 }
573 else
574 {
575 /* If ptid is a wildcard, resume all matching threads (they won't run
576 until the process is continued however). */
577 for (thread_info *tp : all_non_exited_threads (target, ptid))
578 if (ptrace (PT_RESUME, tp->ptid.pid (), NULL, tp->ptid.lwp ()) == -1)
579 perror_with_name (("ptrace"));
580 }
581
582 if (step)
583 {
584 for (thread_info *tp : all_non_exited_threads (target, ptid))
585 if (ptrace (PT_SETSTEP, tp->ptid.pid (), NULL, tp->ptid.lwp ()) == -1)
586 perror_with_name (("ptrace"));
587 }
588 else
589 {
590 for (thread_info *tp : all_non_exited_threads (target, ptid))
591 if (ptrace (PT_CLEARSTEP, tp->ptid.pid (), NULL, tp->ptid.lwp ()) == -1)
592 perror_with_name (("ptrace"));
593 }
594
595 if (catch_syscall_enabled () > 0)
596 request = PT_SYSCALL;
597 else
598 request = PT_CONTINUE;
599
600 /* An address of (void *)1 tells ptrace to continue from
601 where it was. If GDB wanted it to start some other way, we have
602 already written a new program counter value to the child. */
603 if (ptrace (request, ptid.pid (), (void *)1, gdb_signal_to_host (signal)) == -1)
604 perror_with_name (("ptrace"));
605 }
606
607 /* Resume execution of thread PTID, or all threads of all inferiors
608 if PTID is -1. If STEP is nonzero, single-step it. If SIGNAL is nonzero,
609 give it that signal. */
610
611 void
612 nbsd_nat_target::resume (ptid_t ptid, int step, enum gdb_signal signal)
613 {
614 if (minus_one_ptid != ptid)
615 nbsd_resume (this, ptid, step, signal);
616 else
617 {
618 for (inferior *inf : all_non_exited_inferiors (this))
619 nbsd_resume (this, ptid_t (inf->pid, 0, 0), step, signal);
620 }
621 }
622
623 /* Implement a safe wrapper around waitpid(). */
624
625 static pid_t
626 nbsd_wait (ptid_t ptid, struct target_waitstatus *ourstatus, int options)
627 {
628 pid_t pid;
629 int status;
630
631 set_sigint_trap ();
632
633 do
634 {
635 /* The common code passes WNOHANG that leads to crashes, overwrite it. */
636 pid = waitpid (ptid.pid (), &status, 0);
637 }
638 while (pid == -1 && errno == EINTR);
639
640 clear_sigint_trap ();
641
642 if (pid == -1)
643 perror_with_name (_("Child process unexpectedly missing"));
644
645 store_waitstatus (ourstatus, status);
646 return pid;
647 }
648
649 /* Wait for the child specified by PTID to do something. Return the
650 process ID of the child, or MINUS_ONE_PTID in case of error; store
651 the status in *OURSTATUS. */
652
653 ptid_t
654 nbsd_nat_target::wait (ptid_t ptid, struct target_waitstatus *ourstatus,
655 int target_options)
656 {
657 pid_t pid = nbsd_wait (ptid, ourstatus, target_options);
658 ptid_t wptid = ptid_t (pid);
659
660 /* If the child stopped, keep investigating its status. */
661 if (ourstatus->kind != TARGET_WAITKIND_STOPPED)
662 return wptid;
663
664 /* Extract the event and thread that received a signal. */
665 ptrace_siginfo_t psi;
666 if (ptrace (PT_GET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
667 perror_with_name (("ptrace"));
668
669 /* Pick child's siginfo_t. */
670 siginfo_t *si = &psi.psi_siginfo;
671
672 int lwp = psi.psi_lwpid;
673
674 int signo = si->si_signo;
675 const int code = si->si_code;
676
677 /* Construct PTID with a specified thread that received the event.
678 If a signal was targeted to the whole process, lwp is 0. */
679 wptid = ptid_t (pid, lwp, 0);
680
681 /* Bail out on non-debugger oriented signals.. */
682 if (signo != SIGTRAP)
683 return wptid;
684
685 /* Stop examining non-debugger oriented SIGTRAP codes. */
686 if (code <= SI_USER || code == SI_NOINFO)
687 return wptid;
688
689 if (in_thread_list (this, ptid_t (pid)))
690 thread_change_ptid (this, ptid_t (pid), wptid);
691
692 if (code == TRAP_EXEC)
693 {
694 ourstatus->kind = TARGET_WAITKIND_EXECD;
695 ourstatus->value.execd_pathname = xstrdup (pid_to_exec_file (pid));
696 return wptid;
697 }
698
699 if (code == TRAP_TRACE)
700 {
701 /* Unhandled at this level. */
702 return wptid;
703 }
704
705 if (code == TRAP_SCE || code == TRAP_SCX)
706 {
707 int sysnum = si->si_sysnum;
708
709 if (!catch_syscall_enabled () || !catching_syscall_number (sysnum))
710 {
711 /* If the core isn't interested in this event, ignore it. */
712 ourstatus->kind = TARGET_WAITKIND_SPURIOUS;
713 return wptid;
714 }
715
716 ourstatus->kind =
717 (code == TRAP_SCE) ? TARGET_WAITKIND_SYSCALL_ENTRY :
718 TARGET_WAITKIND_SYSCALL_RETURN;
719 ourstatus->value.syscall_number = sysnum;
720 return wptid;
721 }
722
723 if (code == TRAP_BRKPT)
724 {
725 /* Unhandled at this level. */
726 return wptid;
727 }
728
729 /* Unclassified SIGTRAP event. */
730 ourstatus->kind = TARGET_WAITKIND_SPURIOUS;
731 return wptid;
732 }
733
734 /* Implement the "insert_exec_catchpoint" target_ops method. */
735
736 int
737 nbsd_nat_target::insert_exec_catchpoint (int pid)
738 {
739 /* Nothing to do. */
740 return 0;
741 }
742
743 /* Implement the "remove_exec_catchpoint" target_ops method. */
744
745 int
746 nbsd_nat_target::remove_exec_catchpoint (int pid)
747 {
748 /* Nothing to do. */
749 return 0;
750 }
751
752 /* Implement the "set_syscall_catchpoint" target_ops method. */
753
754 int
755 nbsd_nat_target::set_syscall_catchpoint (int pid, bool needed,
756 int any_count,
757 gdb::array_view<const int> syscall_counts)
758 {
759 /* Ignore the arguments. inf-ptrace.c will use PT_SYSCALL which
760 will catch all system call entries and exits. The system calls
761 are filtered by GDB rather than the kernel. */
762 return 0;
763 }
This page took 0.045654 seconds and 4 git commands to generate.