Change boolean options to bool instead of int
[deliverable/binutils-gdb.git] / gdb / solib-aix.c
1 /* Copyright (C) 2013-2019 Free Software Foundation, Inc.
2
3 This file is part of GDB.
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 3 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>. */
17
18 #include "defs.h"
19 #include "solib-aix.h"
20 #include "solist.h"
21 #include "inferior.h"
22 #include "gdb_bfd.h"
23 #include "gdbcore.h"
24 #include "objfiles.h"
25 #include "symtab.h"
26 #include "xcoffread.h"
27 #include "observable.h"
28 #include "gdbcmd.h"
29 #include "gdbsupport/scope-exit.h"
30
31 /* Variable controlling the output of the debugging traces for
32 this module. */
33 static bool solib_aix_debug;
34
35 /* Our private data in struct so_list. */
36
37 struct lm_info_aix : public lm_info_base
38 {
39 /* The name of the file mapped by the loader. Apart from the entry
40 for the main executable, this is usually a shared library (which,
41 on AIX, is an archive library file, created using the "ar"
42 command). */
43 std::string filename;
44
45 /* The name of the shared object file with the actual dynamic
46 loading dependency. This may be empty (Eg. main executable). */
47 std::string member_name;
48
49 /* The address in inferior memory where the text section got mapped. */
50 CORE_ADDR text_addr = 0;
51
52 /* The size of the text section, obtained via the loader data. */
53 ULONGEST text_size = 0;
54
55 /* The address in inferior memory where the data section got mapped. */
56 CORE_ADDR data_addr = 0;
57
58 /* The size of the data section, obtained via the loader data. */
59 ULONGEST data_size = 0;
60 };
61
62 /* This module's per-inferior data. */
63
64 struct solib_aix_inferior_data
65 {
66 /* The list of shared libraries.
67
68 Note that the first element of this list is always the main
69 executable, which is not technically a shared library. But
70 we need that information to perform its relocation, and
71 the same principles applied to shared libraries also apply
72 to the main executable. So it's simpler to keep it as part
73 of this list. */
74 gdb::optional<std::vector<lm_info_aix>> library_list;
75 };
76
77 /* Key to our per-inferior data. */
78 static inferior_key<solib_aix_inferior_data> solib_aix_inferior_data_handle;
79
80 /* Return this module's data for the given inferior.
81 If none is found, add a zero'ed one now. */
82
83 static struct solib_aix_inferior_data *
84 get_solib_aix_inferior_data (struct inferior *inf)
85 {
86 struct solib_aix_inferior_data *data;
87
88 data = solib_aix_inferior_data_handle.get (inf);
89 if (data == NULL)
90 data = solib_aix_inferior_data_handle.emplace (inf);
91
92 return data;
93 }
94
95 #if !defined(HAVE_LIBEXPAT)
96
97 /* Dummy implementation if XML support is not compiled in. */
98
99 static gdb::optional<std::vector<lm_info_aix>>
100 solib_aix_parse_libraries (const char *library)
101 {
102 static int have_warned;
103
104 if (!have_warned)
105 {
106 have_warned = 1;
107 warning (_("Can not parse XML library list; XML support was disabled "
108 "at compile time"));
109 }
110
111 return {};
112 }
113
114 #else /* HAVE_LIBEXPAT */
115
116 #include "xml-support.h"
117
118 /* Handle the start of a <library> element. */
119
120 static void
121 library_list_start_library (struct gdb_xml_parser *parser,
122 const struct gdb_xml_element *element,
123 void *user_data,
124 std::vector<gdb_xml_value> &attributes)
125 {
126 std::vector<lm_info_aix> *list = (std::vector<lm_info_aix> *) user_data;
127 lm_info_aix item;
128 struct gdb_xml_value *attr;
129
130 attr = xml_find_attribute (attributes, "name");
131 item.filename = (const char *) attr->value.get ();
132
133 attr = xml_find_attribute (attributes, "member");
134 if (attr != NULL)
135 item.member_name = (const char *) attr->value.get ();
136
137 attr = xml_find_attribute (attributes, "text_addr");
138 item.text_addr = * (ULONGEST *) attr->value.get ();
139
140 attr = xml_find_attribute (attributes, "text_size");
141 item.text_size = * (ULONGEST *) attr->value.get ();
142
143 attr = xml_find_attribute (attributes, "data_addr");
144 item.data_addr = * (ULONGEST *) attr->value.get ();
145
146 attr = xml_find_attribute (attributes, "data_size");
147 item.data_size = * (ULONGEST *) attr->value.get ();
148
149 list->push_back (std::move (item));
150 }
151
152 /* Handle the start of a <library-list-aix> element. */
153
154 static void
155 library_list_start_list (struct gdb_xml_parser *parser,
156 const struct gdb_xml_element *element,
157 void *user_data,
158 std::vector<gdb_xml_value> &attributes)
159 {
160 char *version
161 = (char *) xml_find_attribute (attributes, "version")->value.get ();
162
163 if (strcmp (version, "1.0") != 0)
164 gdb_xml_error (parser,
165 _("Library list has unsupported version \"%s\""),
166 version);
167 }
168
169 /* The allowed elements and attributes for an AIX library list
170 described in XML format. The root element is a <library-list-aix>. */
171
172 static const struct gdb_xml_attribute library_attributes[] =
173 {
174 { "name", GDB_XML_AF_NONE, NULL, NULL },
175 { "member", GDB_XML_AF_OPTIONAL, NULL, NULL },
176 { "text_addr", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
177 { "text_size", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
178 { "data_addr", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
179 { "data_size", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
180 { NULL, GDB_XML_AF_NONE, NULL, NULL }
181 };
182
183 static const struct gdb_xml_element library_list_children[] =
184 {
185 { "library", library_attributes, NULL,
186 GDB_XML_EF_REPEATABLE | GDB_XML_EF_OPTIONAL,
187 library_list_start_library, NULL},
188 { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
189 };
190
191 static const struct gdb_xml_attribute library_list_attributes[] =
192 {
193 { "version", GDB_XML_AF_NONE, NULL, NULL },
194 { NULL, GDB_XML_AF_NONE, NULL, NULL }
195 };
196
197 static const struct gdb_xml_element library_list_elements[] =
198 {
199 { "library-list-aix", library_list_attributes, library_list_children,
200 GDB_XML_EF_NONE, library_list_start_list, NULL },
201 { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
202 };
203
204 /* Parse LIBRARY, a string containing the loader info in XML format,
205 and return a vector of lm_info_aix objects.
206
207 Return an empty option if the parsing failed. */
208
209 static gdb::optional<std::vector<lm_info_aix>>
210 solib_aix_parse_libraries (const char *library)
211 {
212 std::vector<lm_info_aix> result;
213
214 if (gdb_xml_parse_quick (_("aix library list"), "library-list-aix.dtd",
215 library_list_elements, library, &result) == 0)
216 return result;
217
218 return {};
219 }
220
221 #endif /* HAVE_LIBEXPAT */
222
223 /* Return the loader info for the given inferior (INF), or an empty
224 option if the list could not be computed.
225
226 Cache the result in per-inferior data, so as to avoid recomputing it
227 each time this function is called.
228
229 If an error occurs while computing this list, and WARNING_MSG
230 is not NULL, then print a warning including WARNING_MSG and
231 a description of the error. */
232
233 static gdb::optional<std::vector<lm_info_aix>> &
234 solib_aix_get_library_list (struct inferior *inf, const char *warning_msg)
235 {
236 struct solib_aix_inferior_data *data;
237
238 /* If already computed, return the cached value. */
239 data = get_solib_aix_inferior_data (inf);
240 if (data->library_list.has_value ())
241 return data->library_list;
242
243 gdb::optional<gdb::char_vector> library_document
244 = target_read_stralloc (current_top_target (), TARGET_OBJECT_LIBRARIES_AIX,
245 NULL);
246 if (!library_document && warning_msg != NULL)
247 {
248 warning (_("%s (failed to read TARGET_OBJECT_LIBRARIES_AIX)"),
249 warning_msg);
250 return data->library_list;
251 }
252
253 if (solib_aix_debug)
254 fprintf_unfiltered (gdb_stdlog,
255 "DEBUG: TARGET_OBJECT_LIBRARIES_AIX = \n%s\n",
256 library_document->data ());
257
258 data->library_list = solib_aix_parse_libraries (library_document->data ());
259 if (!data->library_list.has_value () && warning_msg != NULL)
260 warning (_("%s (missing XML support?)"), warning_msg);
261
262 return data->library_list;
263 }
264
265 /* If the .bss section's VMA is set to an address located before
266 the end of the .data section, causing the two sections to overlap,
267 return the overlap in bytes. Otherwise, return zero.
268
269 Motivation:
270
271 The GNU linker sometimes sets the start address of the .bss session
272 before the end of the .data section, making the 2 sections overlap.
273 The loader appears to handle this situation gracefully, by simply
274 loading the bss section right after the end of the .data section.
275
276 This means that the .data and the .bss sections are sometimes
277 no longer relocated by the same amount. The problem is that
278 the ldinfo data does not contain any information regarding
279 the relocation of the .bss section, assuming that it would be
280 identical to the information provided for the .data section
281 (this is what would normally happen if the program was linked
282 correctly).
283
284 GDB therefore needs to detect those cases, and make the corresponding
285 adjustment to the .bss section offset computed from the ldinfo data
286 when necessary. This function returns the adjustment amount (or
287 zero when no adjustment is needed). */
288
289 static CORE_ADDR
290 solib_aix_bss_data_overlap (bfd *abfd)
291 {
292 struct bfd_section *data_sect, *bss_sect;
293
294 data_sect = bfd_get_section_by_name (abfd, ".data");
295 if (data_sect == NULL)
296 return 0; /* No overlap possible. */
297
298 bss_sect = bfd_get_section_by_name (abfd, ".bss");
299 if (bss_sect == NULL)
300 return 0; /* No overlap possible. */
301
302 /* Assume the problem only occurs with linkers that place the .bss
303 section after the .data section (the problem has only been
304 observed when using the GNU linker, and the default linker
305 script always places the .data and .bss sections in that order). */
306 if (bfd_section_vma (abfd, bss_sect)
307 < bfd_section_vma (abfd, data_sect))
308 return 0;
309
310 if (bfd_section_vma (abfd, bss_sect)
311 < bfd_section_vma (abfd, data_sect) + bfd_get_section_size (data_sect))
312 return ((bfd_section_vma (abfd, data_sect)
313 + bfd_get_section_size (data_sect))
314 - bfd_section_vma (abfd, bss_sect));
315
316 return 0;
317 }
318
319 /* Implement the "relocate_section_addresses" target_so_ops method. */
320
321 static void
322 solib_aix_relocate_section_addresses (struct so_list *so,
323 struct target_section *sec)
324 {
325 struct bfd_section *bfd_sect = sec->the_bfd_section;
326 bfd *abfd = bfd_sect->owner;
327 const char *section_name = bfd_section_name (abfd, bfd_sect);
328 lm_info_aix *info = (lm_info_aix *) so->lm_info;
329
330 if (strcmp (section_name, ".text") == 0)
331 {
332 sec->addr = info->text_addr;
333 sec->endaddr = sec->addr + info->text_size;
334
335 /* The text address given to us by the loader contains
336 XCOFF headers, so we need to adjust by this much. */
337 sec->addr += bfd_sect->filepos;
338 }
339 else if (strcmp (section_name, ".data") == 0)
340 {
341 sec->addr = info->data_addr;
342 sec->endaddr = sec->addr + info->data_size;
343 }
344 else if (strcmp (section_name, ".bss") == 0)
345 {
346 /* The information provided by the loader does not include
347 the address of the .bss section, but we know that it gets
348 relocated by the same offset as the .data section. So,
349 compute the relocation offset for the .data section, and
350 apply it to the .bss section as well. If the .data section
351 is not defined (which seems highly unlikely), do our best
352 by assuming no relocation. */
353 struct bfd_section *data_sect
354 = bfd_get_section_by_name (abfd, ".data");
355 CORE_ADDR data_offset = 0;
356
357 if (data_sect != NULL)
358 data_offset = info->data_addr - bfd_section_vma (abfd, data_sect);
359
360 sec->addr = bfd_section_vma (abfd, bfd_sect) + data_offset;
361 sec->addr += solib_aix_bss_data_overlap (abfd);
362 sec->endaddr = sec->addr + bfd_section_size (abfd, bfd_sect);
363 }
364 else
365 {
366 /* All other sections should not be relocated. */
367 sec->addr = bfd_section_vma (abfd, bfd_sect);
368 sec->endaddr = sec->addr + bfd_section_size (abfd, bfd_sect);
369 }
370 }
371
372 /* Implement the "free_so" target_so_ops method. */
373
374 static void
375 solib_aix_free_so (struct so_list *so)
376 {
377 lm_info_aix *li = (lm_info_aix *) so->lm_info;
378
379 if (solib_aix_debug)
380 fprintf_unfiltered (gdb_stdlog, "DEBUG: solib_aix_free_so (%s)\n",
381 so->so_name);
382
383 delete li;
384 }
385
386 /* Implement the "clear_solib" target_so_ops method. */
387
388 static void
389 solib_aix_clear_solib (void)
390 {
391 /* Nothing needed. */
392 }
393
394 /* Compute and return the OBJFILE's section_offset array, using
395 the associated loader info (INFO).
396
397 The resulting array is computed on the heap and must be
398 deallocated after use. */
399
400 static gdb::unique_xmalloc_ptr<struct section_offsets>
401 solib_aix_get_section_offsets (struct objfile *objfile,
402 lm_info_aix *info)
403 {
404 bfd *abfd = objfile->obfd;
405
406 gdb::unique_xmalloc_ptr<struct section_offsets> offsets
407 (XCNEWVEC (struct section_offsets, objfile->num_sections));
408
409 /* .text */
410
411 if (objfile->sect_index_text != -1)
412 {
413 struct bfd_section *sect
414 = objfile->sections[objfile->sect_index_text].the_bfd_section;
415
416 offsets->offsets[objfile->sect_index_text]
417 = info->text_addr + sect->filepos - bfd_section_vma (abfd, sect);
418 }
419
420 /* .data */
421
422 if (objfile->sect_index_data != -1)
423 {
424 struct bfd_section *sect
425 = objfile->sections[objfile->sect_index_data].the_bfd_section;
426
427 offsets->offsets[objfile->sect_index_data]
428 = info->data_addr - bfd_section_vma (abfd, sect);
429 }
430
431 /* .bss
432
433 The offset of the .bss section should be identical to the offset
434 of the .data section. If no .data section (which seems hard to
435 believe it is possible), assume it is zero. */
436
437 if (objfile->sect_index_bss != -1
438 && objfile->sect_index_data != -1)
439 {
440 offsets->offsets[objfile->sect_index_bss]
441 = (offsets->offsets[objfile->sect_index_data]
442 + solib_aix_bss_data_overlap (abfd));
443 }
444
445 /* All other sections should not need relocation. */
446
447 return offsets;
448 }
449
450 /* Implement the "solib_create_inferior_hook" target_so_ops method. */
451
452 static void
453 solib_aix_solib_create_inferior_hook (int from_tty)
454 {
455 const char *warning_msg = "unable to relocate main executable";
456
457 /* We need to relocate the main executable... */
458
459 gdb::optional<std::vector<lm_info_aix>> &library_list
460 = solib_aix_get_library_list (current_inferior (), warning_msg);
461 if (!library_list.has_value ())
462 return; /* Warning already printed. */
463
464 if (library_list->empty ())
465 {
466 warning (_("unable to relocate main executable (no info from loader)"));
467 return;
468 }
469
470 lm_info_aix &exec_info = (*library_list)[0];
471 if (symfile_objfile != NULL)
472 {
473 gdb::unique_xmalloc_ptr<struct section_offsets> offsets
474 = solib_aix_get_section_offsets (symfile_objfile, &exec_info);
475
476 objfile_relocate (symfile_objfile, offsets.get ());
477 }
478 }
479
480 /* Implement the "current_sos" target_so_ops method. */
481
482 static struct so_list *
483 solib_aix_current_sos (void)
484 {
485 struct so_list *start = NULL, *last = NULL;
486 int ix;
487
488 gdb::optional<std::vector<lm_info_aix>> &library_list
489 = solib_aix_get_library_list (current_inferior (), NULL);
490 if (!library_list.has_value ())
491 return NULL;
492
493 /* Build a struct so_list for each entry on the list.
494 We skip the first entry, since this is the entry corresponding
495 to the main executable, not a shared library. */
496 for (ix = 1; ix < library_list->size (); ix++)
497 {
498 struct so_list *new_solib = XCNEW (struct so_list);
499 std::string so_name;
500
501 lm_info_aix &info = (*library_list)[ix];
502 if (info.member_name.empty ())
503 {
504 /* INFO.FILENAME is probably not an archive, but rather
505 a shared object. Unusual, but it should be possible
506 to link a program against a shared object directory,
507 without having to put it in an archive first. */
508 so_name = info.filename;
509 }
510 else
511 {
512 /* This is the usual case on AIX, where the shared object
513 is a member of an archive. Create a synthetic so_name
514 that follows the same convention as AIX's ldd tool
515 (Eg: "/lib/libc.a(shr.o)"). */
516 so_name = string_printf ("%s(%s)", info.filename.c_str (),
517 info.member_name.c_str ());
518 }
519 strncpy (new_solib->so_original_name, so_name.c_str (),
520 SO_NAME_MAX_PATH_SIZE - 1);
521 new_solib->so_name[SO_NAME_MAX_PATH_SIZE - 1] = '\0';
522 memcpy (new_solib->so_name, new_solib->so_original_name,
523 SO_NAME_MAX_PATH_SIZE);
524 new_solib->lm_info = new lm_info_aix (info);
525
526 /* Add it to the list. */
527 if (!start)
528 last = start = new_solib;
529 else
530 {
531 last->next = new_solib;
532 last = new_solib;
533 }
534 }
535
536 return start;
537 }
538
539 /* Implement the "open_symbol_file_object" target_so_ops method. */
540
541 static int
542 solib_aix_open_symbol_file_object (int from_tty)
543 {
544 return 0;
545 }
546
547 /* Implement the "in_dynsym_resolve_code" target_so_ops method. */
548
549 static int
550 solib_aix_in_dynsym_resolve_code (CORE_ADDR pc)
551 {
552 return 0;
553 }
554
555 /* Implement the "bfd_open" target_so_ops method. */
556
557 static gdb_bfd_ref_ptr
558 solib_aix_bfd_open (const char *pathname)
559 {
560 /* The pathname is actually a synthetic filename with the following
561 form: "/path/to/sharedlib(member.o)" (double-quotes excluded).
562 split this into archive name and member name.
563
564 FIXME: This is a little hacky. Perhaps we should provide access
565 to the solib's lm_info here? */
566 const int path_len = strlen (pathname);
567 const char *sep;
568 int filename_len;
569 int found_file;
570
571 if (pathname[path_len - 1] != ')')
572 return solib_bfd_open (pathname);
573
574 /* Search for the associated parens. */
575 sep = strrchr (pathname, '(');
576 if (sep == NULL)
577 {
578 /* Should never happen, but recover as best as we can (trying
579 to open pathname without decoding, possibly leading to
580 a failure), rather than triggering an assert failure). */
581 warning (_("missing '(' in shared object pathname: %s"), pathname);
582 return solib_bfd_open (pathname);
583 }
584 filename_len = sep - pathname;
585
586 std::string filename (string_printf ("%.*s", filename_len, pathname));
587 std::string member_name (string_printf ("%.*s", path_len - filename_len - 2,
588 sep + 1));
589
590 /* Calling solib_find makes certain that sysroot path is set properly
591 if program has a dependency on .a archive and sysroot is set via
592 set sysroot command. */
593 gdb::unique_xmalloc_ptr<char> found_pathname
594 = solib_find (filename.c_str (), &found_file);
595 if (found_pathname == NULL)
596 perror_with_name (pathname);
597 gdb_bfd_ref_ptr archive_bfd (solib_bfd_fopen (found_pathname.get (),
598 found_file));
599 if (archive_bfd == NULL)
600 {
601 warning (_("Could not open `%s' as an executable file: %s"),
602 filename.c_str (), bfd_errmsg (bfd_get_error ()));
603 return NULL;
604 }
605
606 if (bfd_check_format (archive_bfd.get (), bfd_object))
607 return archive_bfd;
608
609 if (! bfd_check_format (archive_bfd.get (), bfd_archive))
610 {
611 warning (_("\"%s\": not in executable format: %s."),
612 filename.c_str (), bfd_errmsg (bfd_get_error ()));
613 return NULL;
614 }
615
616 gdb_bfd_ref_ptr object_bfd
617 (gdb_bfd_openr_next_archived_file (archive_bfd.get (), NULL));
618 while (object_bfd != NULL)
619 {
620 if (member_name == object_bfd->filename)
621 break;
622
623 object_bfd = gdb_bfd_openr_next_archived_file (archive_bfd.get (),
624 object_bfd.get ());
625 }
626
627 if (object_bfd == NULL)
628 {
629 warning (_("\"%s\": member \"%s\" missing."), filename.c_str (),
630 member_name.c_str ());
631 return NULL;
632 }
633
634 if (! bfd_check_format (object_bfd.get (), bfd_object))
635 {
636 warning (_("%s(%s): not in object format: %s."),
637 filename.c_str (), member_name.c_str (),
638 bfd_errmsg (bfd_get_error ()));
639 return NULL;
640 }
641
642 /* Override the returned bfd's name with the name returned from solib_find
643 along with appended parenthesized member name in order to allow commands
644 listing all shared libraries to display. Otherwise, we would only be
645 displaying the name of the archive member object. */
646 bfd_set_filename (object_bfd.get (),
647 xstrprintf ("%s%s",
648 bfd_get_filename (archive_bfd.get ()),
649 sep));
650
651 return object_bfd;
652 }
653
654 /* Return the obj_section corresponding to OBJFILE's data section,
655 or NULL if not found. */
656 /* FIXME: Define in a more general location? */
657
658 static struct obj_section *
659 data_obj_section_from_objfile (struct objfile *objfile)
660 {
661 struct obj_section *osect;
662
663 ALL_OBJFILE_OSECTIONS (objfile, osect)
664 if (strcmp (bfd_section_name (objfile->obfd, osect->the_bfd_section),
665 ".data") == 0)
666 return osect;
667
668 return NULL;
669 }
670
671 /* Return the TOC value corresponding to the given PC address,
672 or raise an error if the value could not be determined. */
673
674 CORE_ADDR
675 solib_aix_get_toc_value (CORE_ADDR pc)
676 {
677 struct obj_section *pc_osect = find_pc_section (pc);
678 struct obj_section *data_osect;
679 CORE_ADDR result;
680
681 if (pc_osect == NULL)
682 error (_("unable to find TOC entry for pc %s "
683 "(no section contains this PC)"),
684 core_addr_to_string (pc));
685
686 data_osect = data_obj_section_from_objfile (pc_osect->objfile);
687 if (data_osect == NULL)
688 error (_("unable to find TOC entry for pc %s "
689 "(%s has no data section)"),
690 core_addr_to_string (pc), objfile_name (pc_osect->objfile));
691
692 result = (obj_section_addr (data_osect)
693 + xcoff_get_toc_offset (pc_osect->objfile));
694 if (solib_aix_debug)
695 fprintf_unfiltered (gdb_stdlog,
696 "DEBUG: solib_aix_get_toc_value (pc=%s) -> %s\n",
697 core_addr_to_string (pc),
698 core_addr_to_string (result));
699
700 return result;
701 }
702
703 /* This module's normal_stop observer. */
704
705 static void
706 solib_aix_normal_stop_observer (struct bpstats *unused_1, int unused_2)
707 {
708 struct solib_aix_inferior_data *data
709 = get_solib_aix_inferior_data (current_inferior ());
710
711 /* The inferior execution has been resumed, and it just stopped
712 again. This means that the list of shared libraries may have
713 evolved. Reset our cached value. */
714 data->library_list.reset ();
715 }
716
717 /* Implements the "show debug aix-solib" command. */
718
719 static void
720 show_solib_aix_debug (struct ui_file *file, int from_tty,
721 struct cmd_list_element *c, const char *value)
722 {
723 fprintf_filtered (file, _("solib-aix debugging is %s.\n"), value);
724 }
725
726 /* The target_so_ops for AIX targets. */
727 struct target_so_ops solib_aix_so_ops;
728
729 void
730 _initialize_solib_aix (void)
731 {
732 solib_aix_so_ops.relocate_section_addresses
733 = solib_aix_relocate_section_addresses;
734 solib_aix_so_ops.free_so = solib_aix_free_so;
735 solib_aix_so_ops.clear_solib = solib_aix_clear_solib;
736 solib_aix_so_ops.solib_create_inferior_hook
737 = solib_aix_solib_create_inferior_hook;
738 solib_aix_so_ops.current_sos = solib_aix_current_sos;
739 solib_aix_so_ops.open_symbol_file_object
740 = solib_aix_open_symbol_file_object;
741 solib_aix_so_ops.in_dynsym_resolve_code
742 = solib_aix_in_dynsym_resolve_code;
743 solib_aix_so_ops.bfd_open = solib_aix_bfd_open;
744
745 gdb::observers::normal_stop.attach (solib_aix_normal_stop_observer);
746
747 /* Debug this file's internals. */
748 add_setshow_boolean_cmd ("aix-solib", class_maintenance,
749 &solib_aix_debug, _("\
750 Control the debugging traces for the solib-aix module."), _("\
751 Show whether solib-aix debugging traces are enabled."), _("\
752 When on, solib-aix debugging traces are enabled."),
753 NULL,
754 show_solib_aix_debug,
755 &setdebuglist, &showdebuglist);
756 }
This page took 0.064345 seconds and 5 git commands to generate.