Commit | Line | Data |
---|---|---|
ea5bc2a6 | 1 | /* Common target-dependent code for NetBSD systems. |
76a9d10f | 2 | |
b811d2c2 | 3 | Copyright (C) 2002-2020 Free Software Foundation, Inc. |
76a9d10f | 4 | |
ea5bc2a6 JT |
5 | Contributed by Wasabi Systems, Inc. |
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 |
ea5bc2a6 | 12 | (at your option) any later version. |
a9762ec7 | 13 | |
ea5bc2a6 JT |
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. | |
a9762ec7 | 18 | |
ea5bc2a6 | 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/>. */ |
ea5bc2a6 JT |
21 | |
22 | #include "defs.h" | |
206c98a6 | 23 | #include "auxv.h" |
ea5bc2a6 | 24 | #include "solib-svr4.h" |
63807e1d | 25 | #include "nbsd-tdep.h" |
79743962 | 26 | #include "gdbarch.h" |
063f8e80 | 27 | #include "objfiles.h" |
b68b1b58 | 28 | #include "xml-syscall.h" |
ea5bc2a6 | 29 | |
54b8cbd0 KR |
30 | /* Flags in the 'kve_protection' field in struct kinfo_vmentry. These |
31 | match the KVME_PROT_* constants in <sys/sysctl.h>. */ | |
32 | ||
33 | #define KINFO_VME_PROT_READ 0x00000001 | |
34 | #define KINFO_VME_PROT_WRITE 0x00000002 | |
35 | #define KINFO_VME_PROT_EXEC 0x00000004 | |
36 | ||
37 | /* Flags in the 'kve_flags' field in struct kinfo_vmentry. These | |
38 | match the KVME_FLAG_* constants in <sys/sysctl.h>. */ | |
39 | ||
40 | #define KINFO_VME_FLAG_COW 0x00000001 | |
41 | #define KINFO_VME_FLAG_NEEDS_COPY 0x00000002 | |
42 | #define KINFO_VME_FLAG_NOCOREDUMP 0x00000004 | |
43 | #define KINFO_VME_FLAG_PAGEABLE 0x00000008 | |
44 | #define KINFO_VME_FLAG_GROWS_UP 0x00000010 | |
45 | #define KINFO_VME_FLAG_GROWS_DOWN 0x00000020 | |
46 | ||
76a9d10f MK |
47 | /* FIXME: kettenis/20060115: We should really eliminate the next two |
48 | functions completely. */ | |
ea5bc2a6 | 49 | |
ea5bc2a6 JT |
50 | struct link_map_offsets * |
51 | nbsd_ilp32_solib_svr4_fetch_link_map_offsets (void) | |
52 | { | |
76a9d10f | 53 | return svr4_ilp32_fetch_link_map_offsets (); |
ea5bc2a6 JT |
54 | } |
55 | ||
56 | struct link_map_offsets * | |
57 | nbsd_lp64_solib_svr4_fetch_link_map_offsets (void) | |
58 | { | |
76a9d10f | 59 | return svr4_lp64_fetch_link_map_offsets (); |
ea5bc2a6 | 60 | } |
3d9b49b0 JT |
61 | |
62 | int | |
2c02bd72 | 63 | nbsd_pc_in_sigtramp (CORE_ADDR pc, const char *func_name) |
3d9b49b0 JT |
64 | { |
65 | /* Check for libc-provided signal trampoline. All such trampolines | |
66 | have function names which begin with "__sigtramp". */ | |
67 | ||
68 | return (func_name != NULL | |
61012eef | 69 | && startswith (func_name, "__sigtramp")); |
3d9b49b0 | 70 | } |
79743962 KR |
71 | |
72 | /* This enum is derived from NETBSD's <sys/signal.h>. */ | |
73 | ||
74 | enum | |
75 | { | |
76 | NBSD_SIGHUP = 1, | |
77 | NBSD_SIGINT = 2, | |
78 | NBSD_SIGQUIT = 3, | |
79 | NBSD_SIGILL = 4, | |
80 | NBSD_SIGTRAP = 5, | |
81 | NBSD_SIGABRT = 6, | |
82 | NBSD_SIGEMT = 7, | |
83 | NBSD_SIGFPE = 8, | |
84 | NBSD_SIGKILL = 9, | |
85 | NBSD_SIGBUS = 10, | |
86 | NBSD_SIGSEGV = 11, | |
87 | NBSD_SIGSYS = 12, | |
88 | NBSD_SIGPIPE = 13, | |
89 | NBSD_SIGALRM = 14, | |
90 | NBSD_SIGTERM = 15, | |
91 | NBSD_SIGURG = 16, | |
92 | NBSD_SIGSTOP = 17, | |
93 | NBSD_SIGTSTP = 18, | |
94 | NBSD_SIGCONT = 19, | |
95 | NBSD_SIGCHLD = 20, | |
96 | NBSD_SIGTTIN = 21, | |
97 | NBSD_SIGTTOU = 22, | |
98 | NBSD_SIGIO = 23, | |
99 | NBSD_SIGXCPU = 24, | |
100 | NBSD_SIGXFSZ = 25, | |
101 | NBSD_SIGVTALRM = 26, | |
102 | NBSD_SIGPROF = 27, | |
103 | NBSD_SIGWINCH = 28, | |
104 | NBSD_SIGINFO = 29, | |
105 | NBSD_SIGUSR1 = 30, | |
106 | NBSD_SIGUSR2 = 31, | |
107 | NBSD_SIGPWR = 32, | |
108 | NBSD_SIGRTMIN = 33, | |
109 | NBSD_SIGRTMAX = 63, | |
110 | }; | |
111 | ||
112 | /* Implement the "gdb_signal_from_target" gdbarch method. */ | |
113 | ||
114 | static enum gdb_signal | |
115 | nbsd_gdb_signal_from_target (struct gdbarch *gdbarch, int signal) | |
116 | { | |
117 | switch (signal) | |
118 | { | |
119 | case 0: | |
120 | return GDB_SIGNAL_0; | |
121 | ||
122 | case NBSD_SIGHUP: | |
123 | return GDB_SIGNAL_HUP; | |
124 | ||
125 | case NBSD_SIGINT: | |
126 | return GDB_SIGNAL_INT; | |
127 | ||
128 | case NBSD_SIGQUIT: | |
129 | return GDB_SIGNAL_QUIT; | |
130 | ||
131 | case NBSD_SIGILL: | |
132 | return GDB_SIGNAL_ILL; | |
133 | ||
134 | case NBSD_SIGTRAP: | |
135 | return GDB_SIGNAL_TRAP; | |
136 | ||
137 | case NBSD_SIGABRT: | |
138 | return GDB_SIGNAL_ABRT; | |
139 | ||
140 | case NBSD_SIGEMT: | |
141 | return GDB_SIGNAL_EMT; | |
142 | ||
143 | case NBSD_SIGFPE: | |
144 | return GDB_SIGNAL_FPE; | |
145 | ||
146 | case NBSD_SIGKILL: | |
147 | return GDB_SIGNAL_KILL; | |
148 | ||
149 | case NBSD_SIGBUS: | |
150 | return GDB_SIGNAL_BUS; | |
151 | ||
152 | case NBSD_SIGSEGV: | |
153 | return GDB_SIGNAL_SEGV; | |
154 | ||
155 | case NBSD_SIGSYS: | |
156 | return GDB_SIGNAL_SYS; | |
157 | ||
158 | case NBSD_SIGPIPE: | |
159 | return GDB_SIGNAL_PIPE; | |
160 | ||
161 | case NBSD_SIGALRM: | |
162 | return GDB_SIGNAL_ALRM; | |
163 | ||
164 | case NBSD_SIGTERM: | |
165 | return GDB_SIGNAL_TERM; | |
166 | ||
167 | case NBSD_SIGURG: | |
168 | return GDB_SIGNAL_URG; | |
169 | ||
170 | case NBSD_SIGSTOP: | |
171 | return GDB_SIGNAL_STOP; | |
172 | ||
173 | case NBSD_SIGTSTP: | |
174 | return GDB_SIGNAL_TSTP; | |
175 | ||
176 | case NBSD_SIGCONT: | |
177 | return GDB_SIGNAL_CONT; | |
178 | ||
179 | case NBSD_SIGCHLD: | |
180 | return GDB_SIGNAL_CHLD; | |
181 | ||
182 | case NBSD_SIGTTIN: | |
183 | return GDB_SIGNAL_TTIN; | |
184 | ||
185 | case NBSD_SIGTTOU: | |
186 | return GDB_SIGNAL_TTOU; | |
187 | ||
188 | case NBSD_SIGIO: | |
189 | return GDB_SIGNAL_IO; | |
190 | ||
191 | case NBSD_SIGXCPU: | |
192 | return GDB_SIGNAL_XCPU; | |
193 | ||
194 | case NBSD_SIGXFSZ: | |
195 | return GDB_SIGNAL_XFSZ; | |
196 | ||
197 | case NBSD_SIGVTALRM: | |
198 | return GDB_SIGNAL_VTALRM; | |
199 | ||
200 | case NBSD_SIGPROF: | |
201 | return GDB_SIGNAL_PROF; | |
202 | ||
203 | case NBSD_SIGWINCH: | |
204 | return GDB_SIGNAL_WINCH; | |
205 | ||
206 | case NBSD_SIGINFO: | |
207 | return GDB_SIGNAL_INFO; | |
208 | ||
209 | case NBSD_SIGUSR1: | |
210 | return GDB_SIGNAL_USR1; | |
211 | ||
212 | case NBSD_SIGUSR2: | |
213 | return GDB_SIGNAL_USR2; | |
214 | ||
215 | case NBSD_SIGPWR: | |
216 | return GDB_SIGNAL_PWR; | |
217 | ||
218 | /* SIGRTMIN and SIGRTMAX are not continuous in <gdb/signals.def>, | |
219 | therefore we have to handle them here. */ | |
220 | case NBSD_SIGRTMIN: | |
221 | return GDB_SIGNAL_REALTIME_33; | |
222 | ||
223 | case NBSD_SIGRTMAX: | |
224 | return GDB_SIGNAL_REALTIME_63; | |
225 | } | |
226 | ||
227 | if (signal >= NBSD_SIGRTMIN + 1 && signal <= NBSD_SIGRTMAX - 1) | |
228 | { | |
229 | int offset = signal - NBSD_SIGRTMIN + 1; | |
230 | ||
231 | return (enum gdb_signal) ((int) GDB_SIGNAL_REALTIME_34 + offset); | |
232 | } | |
233 | ||
234 | return GDB_SIGNAL_UNKNOWN; | |
235 | } | |
236 | ||
237 | /* Implement the "gdb_signal_to_target" gdbarch method. */ | |
238 | ||
239 | static int | |
240 | nbsd_gdb_signal_to_target (struct gdbarch *gdbarch, | |
241 | enum gdb_signal signal) | |
242 | { | |
243 | switch (signal) | |
244 | { | |
245 | case GDB_SIGNAL_0: | |
246 | return 0; | |
247 | ||
248 | case GDB_SIGNAL_HUP: | |
249 | return NBSD_SIGHUP; | |
250 | ||
251 | case GDB_SIGNAL_INT: | |
252 | return NBSD_SIGINT; | |
253 | ||
254 | case GDB_SIGNAL_QUIT: | |
255 | return NBSD_SIGQUIT; | |
256 | ||
257 | case GDB_SIGNAL_ILL: | |
258 | return NBSD_SIGILL; | |
259 | ||
260 | case GDB_SIGNAL_TRAP: | |
261 | return NBSD_SIGTRAP; | |
262 | ||
263 | case GDB_SIGNAL_ABRT: | |
264 | return NBSD_SIGABRT; | |
265 | ||
266 | case GDB_SIGNAL_EMT: | |
267 | return NBSD_SIGEMT; | |
268 | ||
269 | case GDB_SIGNAL_FPE: | |
270 | return NBSD_SIGFPE; | |
271 | ||
272 | case GDB_SIGNAL_KILL: | |
273 | return NBSD_SIGKILL; | |
274 | ||
275 | case GDB_SIGNAL_BUS: | |
276 | return NBSD_SIGBUS; | |
277 | ||
278 | case GDB_SIGNAL_SEGV: | |
279 | return NBSD_SIGSEGV; | |
280 | ||
281 | case GDB_SIGNAL_SYS: | |
282 | return NBSD_SIGSYS; | |
283 | ||
284 | case GDB_SIGNAL_PIPE: | |
285 | return NBSD_SIGPIPE; | |
286 | ||
287 | case GDB_SIGNAL_ALRM: | |
288 | return NBSD_SIGALRM; | |
289 | ||
290 | case GDB_SIGNAL_TERM: | |
291 | return NBSD_SIGTERM; | |
292 | ||
293 | case GDB_SIGNAL_URG: | |
294 | return NBSD_SIGSTOP; | |
295 | ||
296 | case GDB_SIGNAL_TSTP: | |
297 | return NBSD_SIGTSTP; | |
298 | ||
299 | case GDB_SIGNAL_CONT: | |
300 | return NBSD_SIGCONT; | |
301 | ||
302 | case GDB_SIGNAL_CHLD: | |
303 | return NBSD_SIGCHLD; | |
304 | ||
305 | case GDB_SIGNAL_TTIN: | |
306 | return NBSD_SIGTTIN; | |
307 | ||
308 | case GDB_SIGNAL_TTOU: | |
309 | return NBSD_SIGTTOU; | |
310 | ||
311 | case GDB_SIGNAL_IO: | |
312 | return NBSD_SIGIO; | |
313 | ||
314 | case GDB_SIGNAL_XCPU: | |
315 | return NBSD_SIGXCPU; | |
316 | ||
317 | case GDB_SIGNAL_XFSZ: | |
318 | return NBSD_SIGXFSZ; | |
319 | ||
320 | case GDB_SIGNAL_VTALRM: | |
321 | return NBSD_SIGVTALRM; | |
322 | ||
323 | case GDB_SIGNAL_PROF: | |
324 | return NBSD_SIGPROF; | |
325 | ||
326 | case GDB_SIGNAL_WINCH: | |
327 | return NBSD_SIGWINCH; | |
328 | ||
329 | case GDB_SIGNAL_INFO: | |
330 | return NBSD_SIGINFO; | |
331 | ||
332 | case GDB_SIGNAL_USR1: | |
333 | return NBSD_SIGUSR1; | |
334 | ||
335 | case GDB_SIGNAL_USR2: | |
336 | return NBSD_SIGUSR2; | |
337 | ||
338 | case GDB_SIGNAL_PWR: | |
339 | return NBSD_SIGPWR; | |
340 | ||
341 | /* GDB_SIGNAL_REALTIME_33 is not continuous in <gdb/signals.def>, | |
342 | therefore we have to handle it here. */ | |
343 | case GDB_SIGNAL_REALTIME_33: | |
344 | return NBSD_SIGRTMIN; | |
345 | ||
346 | /* Same comment applies to _64. */ | |
347 | case GDB_SIGNAL_REALTIME_63: | |
348 | return NBSD_SIGRTMAX; | |
349 | } | |
350 | ||
351 | if (signal >= GDB_SIGNAL_REALTIME_34 | |
352 | && signal <= GDB_SIGNAL_REALTIME_62) | |
353 | { | |
354 | int offset = signal - GDB_SIGNAL_REALTIME_32; | |
355 | ||
356 | return NBSD_SIGRTMIN + 1 + offset; | |
357 | } | |
358 | ||
359 | return -1; | |
360 | } | |
361 | ||
063f8e80 KR |
362 | /* Shared library resolver handling. */ |
363 | ||
364 | static CORE_ADDR | |
365 | nbsd_skip_solib_resolver (struct gdbarch *gdbarch, CORE_ADDR pc) | |
366 | { | |
367 | struct bound_minimal_symbol msym; | |
368 | ||
369 | msym = lookup_minimal_symbol ("_rtld_bind_start", NULL, NULL); | |
370 | if (msym.minsym && BMSYMBOL_VALUE_ADDRESS (msym) == pc) | |
371 | return frame_unwind_caller_pc (get_current_frame ()); | |
372 | else | |
373 | return find_solib_trampoline_target (get_current_frame (), pc); | |
374 | } | |
375 | ||
4d46f402 KR |
376 | static struct gdbarch_data *nbsd_gdbarch_data_handle; |
377 | ||
378 | struct nbsd_gdbarch_data | |
379 | { | |
380 | struct type *siginfo_type; | |
381 | }; | |
382 | ||
383 | static void * | |
384 | init_nbsd_gdbarch_data (struct gdbarch *gdbarch) | |
385 | { | |
386 | return GDBARCH_OBSTACK_ZALLOC (gdbarch, struct nbsd_gdbarch_data); | |
387 | } | |
388 | ||
389 | static struct nbsd_gdbarch_data * | |
390 | get_nbsd_gdbarch_data (struct gdbarch *gdbarch) | |
391 | { | |
392 | return ((struct nbsd_gdbarch_data *) | |
393 | gdbarch_data (gdbarch, nbsd_gdbarch_data_handle)); | |
394 | } | |
395 | ||
396 | /* Implement the "get_siginfo_type" gdbarch method. */ | |
397 | ||
398 | static struct type * | |
399 | nbsd_get_siginfo_type (struct gdbarch *gdbarch) | |
400 | { | |
401 | nbsd_gdbarch_data *nbsd_gdbarch_data = get_nbsd_gdbarch_data (gdbarch); | |
402 | if (nbsd_gdbarch_data->siginfo_type != NULL) | |
403 | return nbsd_gdbarch_data->siginfo_type; | |
404 | ||
405 | type *char_type = builtin_type (gdbarch)->builtin_char; | |
406 | type *int_type = builtin_type (gdbarch)->builtin_int; | |
407 | type *long_type = builtin_type (gdbarch)->builtin_long; | |
408 | ||
409 | type *void_ptr_type | |
410 | = lookup_pointer_type (builtin_type (gdbarch)->builtin_void); | |
411 | ||
412 | type *int32_type = builtin_type (gdbarch)->builtin_int32; | |
413 | type *uint32_type = builtin_type (gdbarch)->builtin_uint32; | |
414 | type *uint64_type = builtin_type (gdbarch)->builtin_uint64; | |
415 | ||
416 | bool lp64 = TYPE_LENGTH (void_ptr_type) == 8; | |
417 | size_t char_bits = gdbarch_addressable_memory_unit_size (gdbarch) * 8; | |
418 | ||
419 | /* pid_t */ | |
420 | type *pid_type = arch_type (gdbarch, TYPE_CODE_TYPEDEF, | |
421 | TYPE_LENGTH (int32_type) * char_bits, "pid_t"); | |
422 | TYPE_TARGET_TYPE (pid_type) = int32_type; | |
423 | ||
424 | /* uid_t */ | |
425 | type *uid_type = arch_type (gdbarch, TYPE_CODE_TYPEDEF, | |
426 | TYPE_LENGTH (uint32_type) * char_bits, "uid_t"); | |
427 | TYPE_TARGET_TYPE (uid_type) = uint32_type; | |
428 | ||
429 | /* clock_t */ | |
430 | type *clock_type = arch_type (gdbarch, TYPE_CODE_TYPEDEF, | |
431 | TYPE_LENGTH (int_type) * char_bits, "clock_t"); | |
432 | TYPE_TARGET_TYPE (clock_type) = int_type; | |
433 | ||
434 | /* lwpid_t */ | |
435 | type *lwpid_type = arch_type (gdbarch, TYPE_CODE_TYPEDEF, | |
436 | TYPE_LENGTH (int32_type) * char_bits, | |
437 | "lwpid_t"); | |
438 | TYPE_TARGET_TYPE (lwpid_type) = int32_type; | |
439 | ||
440 | /* union sigval */ | |
441 | type *sigval_type = arch_composite_type (gdbarch, NULL, TYPE_CODE_UNION); | |
442 | sigval_type->set_name (gdbarch_obstack_strdup (gdbarch, "sigval")); | |
443 | append_composite_type_field (sigval_type, "sival_int", int_type); | |
444 | append_composite_type_field (sigval_type, "sival_ptr", void_ptr_type); | |
445 | ||
446 | /* union _option */ | |
447 | type *option_type = arch_composite_type (gdbarch, NULL, TYPE_CODE_UNION); | |
448 | option_type->set_name (gdbarch_obstack_strdup (gdbarch, "_option")); | |
449 | append_composite_type_field (option_type, "_pe_other_pid", pid_type); | |
450 | append_composite_type_field (option_type, "_pe_lwp", lwpid_type); | |
451 | ||
452 | /* union _reason */ | |
453 | type *reason_type = arch_composite_type (gdbarch, NULL, TYPE_CODE_UNION); | |
454 | ||
455 | /* _rt */ | |
456 | type *t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
457 | append_composite_type_field (t, "_pid", pid_type); | |
458 | append_composite_type_field (t, "_uid", uid_type); | |
459 | append_composite_type_field (t, "_value", sigval_type); | |
460 | append_composite_type_field (reason_type, "_rt", t); | |
461 | ||
462 | /* _child */ | |
463 | t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
464 | append_composite_type_field (t, "_pid", pid_type); | |
465 | append_composite_type_field (t, "_uid", uid_type); | |
466 | append_composite_type_field (t, "_status", int_type); | |
467 | append_composite_type_field (t, "_utime", clock_type); | |
468 | append_composite_type_field (t, "_stime", clock_type); | |
469 | append_composite_type_field (reason_type, "_child", t); | |
470 | ||
471 | /* _fault */ | |
472 | t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
473 | append_composite_type_field (t, "_addr", void_ptr_type); | |
474 | append_composite_type_field (t, "_trap", int_type); | |
475 | append_composite_type_field (t, "_trap2", int_type); | |
476 | append_composite_type_field (t, "_trap3", int_type); | |
477 | append_composite_type_field (reason_type, "_fault", t); | |
478 | ||
479 | /* _poll */ | |
480 | t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
481 | append_composite_type_field (t, "_band", long_type); | |
482 | append_composite_type_field (t, "_fd", int_type); | |
483 | append_composite_type_field (reason_type, "_poll", t); | |
484 | ||
485 | /* _syscall */ | |
486 | t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
487 | append_composite_type_field (t, "_sysnum", int_type); | |
488 | append_composite_type_field (t, "_retval", | |
489 | init_vector_type (int_type, 2)); | |
490 | append_composite_type_field (t, "_error", int_type); | |
491 | append_composite_type_field (t, "_args", | |
492 | init_vector_type (uint64_type, 8)); | |
493 | append_composite_type_field (reason_type, "_syscall", t); | |
494 | ||
495 | /* _ptrace_state */ | |
496 | t = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
497 | append_composite_type_field (t, "_pe_report_event", int_type); | |
498 | append_composite_type_field (t, "_option", option_type); | |
499 | append_composite_type_field (reason_type, "_ptrace_state", t); | |
500 | ||
501 | /* struct _ksiginfo */ | |
502 | type *ksiginfo_type = arch_composite_type (gdbarch, NULL, TYPE_CODE_STRUCT); | |
503 | ksiginfo_type->set_name (gdbarch_obstack_strdup (gdbarch, "_ksiginfo")); | |
504 | append_composite_type_field (ksiginfo_type, "_signo", int_type); | |
505 | append_composite_type_field (ksiginfo_type, "_code", int_type); | |
506 | append_composite_type_field (ksiginfo_type, "_errno", int_type); | |
507 | if (lp64) | |
508 | append_composite_type_field (ksiginfo_type, "_pad", int_type); | |
509 | append_composite_type_field (ksiginfo_type, "_reason", reason_type); | |
510 | ||
511 | /* union siginfo */ | |
512 | type *siginfo_type = arch_composite_type (gdbarch, NULL, TYPE_CODE_UNION); | |
513 | siginfo_type->set_name (gdbarch_obstack_strdup (gdbarch, "siginfo")); | |
514 | append_composite_type_field (siginfo_type, "si_pad", | |
515 | init_vector_type (char_type, 128)); | |
516 | append_composite_type_field (siginfo_type, "_info", ksiginfo_type); | |
517 | ||
518 | nbsd_gdbarch_data->siginfo_type = siginfo_type; | |
519 | ||
520 | return siginfo_type; | |
521 | } | |
522 | ||
79743962 KR |
523 | /* See nbsd-tdep.h. */ |
524 | ||
54b8cbd0 KR |
525 | void |
526 | nbsd_info_proc_mappings_header (int addr_bit) | |
527 | { | |
528 | printf_filtered (_("Mapped address spaces:\n\n")); | |
529 | if (addr_bit == 64) | |
530 | { | |
531 | printf_filtered (" %18s %18s %10s %10s %9s %s\n", | |
532 | "Start Addr", | |
533 | " End Addr", | |
534 | " Size", " Offset", "Flags ", "File"); | |
535 | } | |
536 | else | |
537 | { | |
538 | printf_filtered ("\t%10s %10s %10s %10s %9s %s\n", | |
539 | "Start Addr", | |
540 | " End Addr", | |
541 | " Size", " Offset", "Flags ", "File"); | |
542 | } | |
543 | } | |
544 | ||
545 | /* Helper function to generate mappings flags for a single VM map | |
546 | entry in 'info proc mappings'. */ | |
547 | ||
548 | static const char * | |
549 | nbsd_vm_map_entry_flags (int kve_flags, int kve_protection) | |
550 | { | |
551 | static char vm_flags[9]; | |
552 | ||
553 | vm_flags[0] = (kve_protection & KINFO_VME_PROT_READ) ? 'r' : '-'; | |
554 | vm_flags[1] = (kve_protection & KINFO_VME_PROT_WRITE) ? 'w' : '-'; | |
555 | vm_flags[2] = (kve_protection & KINFO_VME_PROT_EXEC) ? 'x' : '-'; | |
556 | vm_flags[3] = ' '; | |
557 | vm_flags[4] = (kve_flags & KINFO_VME_FLAG_COW) ? 'C' : '-'; | |
558 | vm_flags[5] = (kve_flags & KINFO_VME_FLAG_NEEDS_COPY) ? 'N' : '-'; | |
559 | vm_flags[6] = (kve_flags & KINFO_VME_FLAG_PAGEABLE) ? 'P' : '-'; | |
560 | vm_flags[7] = (kve_flags & KINFO_VME_FLAG_GROWS_UP) ? 'U' | |
561 | : (kve_flags & KINFO_VME_FLAG_GROWS_DOWN) ? 'D' : '-'; | |
562 | vm_flags[8] = '\0'; | |
563 | ||
564 | return vm_flags; | |
565 | } | |
566 | ||
567 | void | |
568 | nbsd_info_proc_mappings_entry (int addr_bit, ULONGEST kve_start, | |
569 | ULONGEST kve_end, ULONGEST kve_offset, | |
570 | int kve_flags, int kve_protection, | |
571 | const char *kve_path) | |
572 | { | |
573 | if (addr_bit == 64) | |
574 | { | |
575 | printf_filtered (" %18s %18s %10s %10s %9s %s\n", | |
576 | hex_string (kve_start), | |
577 | hex_string (kve_end), | |
578 | hex_string (kve_end - kve_start), | |
579 | hex_string (kve_offset), | |
580 | nbsd_vm_map_entry_flags (kve_flags, kve_protection), | |
581 | kve_path); | |
582 | } | |
583 | else | |
584 | { | |
585 | printf_filtered ("\t%10s %10s %10s %10s %9s %s\n", | |
586 | hex_string (kve_start), | |
587 | hex_string (kve_end), | |
588 | hex_string (kve_end - kve_start), | |
589 | hex_string (kve_offset), | |
590 | nbsd_vm_map_entry_flags (kve_flags, kve_protection), | |
591 | kve_path); | |
592 | } | |
593 | } | |
594 | ||
f94b2e03 KR |
595 | /* Implement the "get_syscall_number" gdbarch method. */ |
596 | ||
597 | static LONGEST | |
598 | nbsd_get_syscall_number (struct gdbarch *gdbarch, thread_info *thread) | |
599 | { | |
600 | ||
601 | /* NetBSD doesn't use gdbarch_get_syscall_number since NetBSD | |
602 | native targets fetch the system call number from the | |
603 | 'si_sysnum' member of siginfo_t in nbsd_nat_target::wait. | |
604 | However, system call catching requires this function to be | |
605 | set. */ | |
606 | ||
607 | internal_error (__FILE__, __LINE__, _("nbsd_get_sycall_number called")); | |
608 | } | |
609 | ||
54b8cbd0 KR |
610 | /* See nbsd-tdep.h. */ |
611 | ||
79743962 KR |
612 | void |
613 | nbsd_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch) | |
614 | { | |
615 | set_gdbarch_gdb_signal_from_target (gdbarch, nbsd_gdb_signal_from_target); | |
616 | set_gdbarch_gdb_signal_to_target (gdbarch, nbsd_gdb_signal_to_target); | |
063f8e80 | 617 | set_gdbarch_skip_solib_resolver (gdbarch, nbsd_skip_solib_resolver); |
206c98a6 | 618 | set_gdbarch_auxv_parse (gdbarch, svr4_auxv_parse); |
4d46f402 | 619 | set_gdbarch_get_siginfo_type (gdbarch, nbsd_get_siginfo_type); |
f94b2e03 KR |
620 | |
621 | /* `catch syscall' */ | |
b68b1b58 | 622 | set_xml_syscall_file_name (gdbarch, "syscalls/netbsd.xml"); |
f94b2e03 | 623 | set_gdbarch_get_syscall_number (gdbarch, nbsd_get_syscall_number); |
79743962 | 624 | } |
4d46f402 KR |
625 | |
626 | void _initialize_nbsd_tdep (); | |
627 | void | |
628 | _initialize_nbsd_tdep () | |
629 | { | |
630 | nbsd_gdbarch_data_handle | |
631 | = gdbarch_data_register_post_init (init_nbsd_gdbarch_data); | |
632 | } |