1 https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=207644
4 diff -u -rup -x testsuite gdb-6.3-orig/gdb/corelow.c gdb-6.3/gdb/corelow.c
5 --- gdb-6.3-orig/gdb/corelow.c 2004-10-08 22:29:46.000000000 +0200
6 +++ gdb-6.3/gdb/corelow.c 2006-12-29 18:51:19.000000000 +0100
9 #include <sys/file.h> /* needed for F_OK and friends */
12 +#include <asm/page.h> /* FIXME: `PAGE_SIZE'! */
13 #include "frame.h" /* required by inferior.h */
17 #include "readline/readline.h"
19 #include "gdb_assert.h"
21 +#include "completer.h"
30 @@ -272,6 +281,369 @@ add_to_thread_list (bfd *abfd, asection
31 inferior_ptid = pid_to_ptid (thread_id); /* Yes, make it current */
34 +static char *object_path;
37 +show_objectdirectories (char *ignore, int from_tty)
39 + puts_filtered ("Object directories searched: ");
40 + puts_filtered (object_path);
41 + puts_filtered ("\n");
45 +init_object_path (void)
47 + object_path = xstrdup ("");
50 +/* Add zero or more directories to the front of the object path. */
53 +objectdirectory_command (char *dirname, int from_tty)
56 + /* FIXME, this goes to "delete dir"... */
59 + if (from_tty && query ("Reinitialize object path to empty? "))
61 + xfree (object_path);
62 + init_object_path ();
67 + mod_path (dirname, &object_path);
70 + show_objectdirectories ((char *) 0, from_tty);
75 + struct objid_cache *next;
79 +static struct objid_cache *objid_cache;
82 +objid_cache_find (ElfW(Word) sum)
84 + struct objid_cache *item;
86 + for (item = objid_cache; item != NULL; item = item->next)
87 + if (item->sum == sum)
88 + return item->filename;
94 +objid_cache_add (const char *filename, ElfW(Word) sum)
96 + const char *filename_old;
97 + struct objid_cache *objid_cache_new;
99 + filename_old = objid_cache_find (sum);
100 + if (filename_old != NULL && strcmp (filename, filename_old) != 0)
101 + warning ("Duplicite checksum of `%s' vs. `%s'", filename_old, filename);
102 + if (filename_old != NULL)
105 + objid_cache_new = xmalloc (sizeof (*objid_cache_new));
106 + objid_cache_new->next = objid_cache;
107 + objid_cache_new->filename = xstrdup (filename);
108 + objid_cache_new->sum = sum;
109 + objid_cache = objid_cache_new;
113 +objid_cache_clear (void)
115 + while (objid_cache)
117 + struct objid_cache *freeing;
119 + freeing = objid_cache;
120 + objid_cache = freeing->next;
121 + xfree (freeing->filename);
127 +objid_locate_file_bfd (bfd *abfd)
131 + Elf_Internal_Ehdr *ehdr;
132 + ElfW(Word) sum = 0;
134 + if (bfd_check_format (abfd, bfd_object) == FALSE)
136 + if (bfd_get_error () != bfd_error_file_not_recognized)
137 + warning ("Error checking binary `%s' (%s)", bfd_get_filename (abfd),
138 + bfd_errmsg (bfd_get_error ()));
141 + /* Non-executable files? Such as the `.o' files. */
142 + if ((bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC)) == 0)
145 + /* `bfd_target_elf_flavour' is required for elf_tdata(). */
146 + if (bfd_get_flavour (abfd) != bfd_target_elf_flavour)
149 + ehdr = elf_tdata (abfd)->elf_header;
151 + for (phi = 0; phi < ehdr->e_phnum; phi++)
153 + Elf_Internal_Phdr *phdr = &elf_tdata (abfd)->phdr[phi];
154 + bfd_size_type remains;
156 + /* Match the same conditions as in libobjid `phdr_callback'! */
157 + /* FIXME: Unify the code. */
158 + if (phdr->p_type != PT_LOAD)
160 + if (!(phdr->p_flags & PF_R))
162 + /* Present? We probably could not checksum such one. */
163 + if (phdr->p_flags & PF_W)
166 + if (bfd_seek (abfd, phdr->p_offset, SEEK_SET) != 0)
168 + warning ("Error seeking binary `%s' to program header #%u (%s)",
169 + bfd_get_filename (abfd), phi, bfd_errmsg (bfd_get_error ()));
172 + remains = phdr->p_filesz;
173 + while (remains > 0)
175 + unsigned char buf[0x10000];
176 + bfd_size_type count;
177 + unsigned char *ptr;
179 + count = min (remains, sizeof (buf));
180 + if (bfd_bread (buf, count, abfd) != count)
182 + warning ("Error reading binary `%s' of program header #%u (%s)",
183 + bfd_get_filename (abfd), phi,
184 + bfd_errmsg (bfd_get_error ()));
188 + for (ptr = buf; ptr < buf + count; ptr++)
189 + sum = sum * 31 + *ptr;
195 + objid_cache_add (bfd_get_filename (abfd), sum);
199 +objid_locate_file (const char *filename)
203 + /* FIXME: Persistent storage - `core_bfd'! */
204 + abfd = bfd_openr (filename, bfd_get_target (core_bfd));
207 + warning ("Error opening binary `%s' (%s)", filename,
208 + bfd_errmsg (bfd_get_error ()));
212 + objid_locate_file_bfd (abfd);
214 + if (!bfd_close (abfd))
216 + warning ("Error closing binary `%s' (%s)", filename,
217 + bfd_errmsg (bfd_get_error ()));
223 +objid_locate_dir (const char *dirname)
226 + struct dirent *dirent;
228 + dir = opendir (dirname);
231 + warning ("Error scanning object directory `%s' (%s)", dirname,
232 + safe_strerror (errno));
235 + while (errno = 0, dirent = readdir (dir))
239 + if (strcmp (dirent->d_name, ".") == 0)
241 + if (strcmp (dirent->d_name, "..") == 0)
243 + targetname = xstrprintf ("%s/%s", dirname, dirent->d_name);
244 + if (dirent->d_type == DT_DIR)
245 + objid_locate_dir (targetname);
246 + if (dirent->d_type == DT_REG)
247 + objid_locate_file (targetname);
248 + xfree (targetname);
251 + warning ("Error reading object directory `%s' (%s)", dirname,
252 + safe_strerror (errno));
253 + if (closedir (dir))
255 + warning ("Error closing object directory `%s' (%s)", dirname,
256 + safe_strerror (errno));
262 +objid_cache_reload (void)
266 + objid_cache_clear ();
268 + if (strcmp (object_path, "") == 0)
271 + for (p = object_path; p; p = p1 ? p1 + 1 : 0)
276 + p1 = strchr (p, DIRNAME_SEPARATOR);
278 + dirname = xstrdup (p);
281 + dirname = xmalloc (p1 + 1 - p);
282 + memcpy (dirname, p, p1 - p);
283 + dirname[p1 - p] = 0;
285 + objid_locate_dir (dirname);
290 +/* HEADER_POINTER is at the place of user data OBJ. */
291 +/* Return TRUE of allocated header has been read to `*header_pointer'. */
293 +objid_locate_scan (bfd *abfd, asection *sect,
294 + ElfW(LibobjidHdr) **header_pointer)
297 + bfd_size_type size = bfd_section_size (abfd, sect);
298 + ElfW(LibobjidHdr) header_local, *header;
300 + if (size < sizeof (header_local))
303 + /* FIXME: `PAGE_SIZE' should be from `auxv'. */
304 + for (offset = 0; offset <= size - sizeof (header_local); offset += PAGE_SIZE)
306 + if (bfd_get_section_contents (abfd, sect, &header_local, offset,
307 + sizeof (header_local)) == FALSE)
309 + if (header_local.magic != ElfW(Magic))
311 + if (header_local.self != bfd_section_vma (abfd, sect) + offset)
313 + if (header_local.self_not != ~header_local.self)
315 + /* Sanity check to avoid loading xmalloc() crashes. */
316 + if (header_local.size > 0x10000)
318 + if (header_local.size < sizeof (*header)
319 + + header_local.obj_count * sizeof (*header->obj))
322 + header = xmalloc (header_local.size);
323 + if (bfd_get_section_contents (abfd, sect, header, offset,
324 + header_local.size) == TRUE)
326 + *header_pointer = header;
335 +objid_exec_load (char *exec_file, int from_tty)
337 + if (exec_bfd == NULL
338 + || query (_("Load the matching executable/symbols \"%s\"? "),
341 + if (catch_command_errors (exec_file_attach,
342 + exec_file, from_tty, RETURN_MASK_ALL))
343 + catch_command_errors (symbol_file_add_main_userloaded,
344 + exec_file, from_tty, RETURN_MASK_ALL);
349 +objid_locate (bfd *core_bfd, int from_tty)
352 + ElfW(LibobjidHdr) *header;
355 + if (bfd_sections_find_if (core_bfd,
356 + (bfd_boolean (*) (bfd *abfd, asection *sect, void *obj))
357 + objid_locate_scan, &header) == NULL)
360 + /* FIXME: Keep the cache more persistent. */
361 + objid_cache_reload ();
363 + for (obji = 0; obji < header->obj_count; obji++)
365 + ElfW(LibobjidObj) *obj = &header->obj[obji];
366 + CORE_ADDR filename_addr = obj->filename;
368 + int filename_errno;
370 + /* Return value 0 is OK - empty strings. */
371 + if (target_read_string (filename_addr, &filename, FILENAME_MAX,
372 + &filename_errno) <= 0 || filename_errno != 0)
373 + warning ("Error reading objid object #%u filename (%s)", obji,
374 + safe_strerror (filename_errno));
377 + const char *filename_found;
379 + filename_found = objid_cache_find (obj->checksum);
380 + if (filename_found != NULL)
382 + /* Main executable? It is the first entry with empty name. */
383 + if (obji == 0 && strcmp (filename, "") == 0)
384 + objid_exec_load ((char *) filename_found, from_tty);
385 + else if (strcmp (filename, "") != 0)
386 + solib_open_map (filename, filename_found);
388 + warning ("Ignoring invalid objid mapping `%s' -> `%s'",
389 + filename, filename_found);
397 /* This routine opens and sets up the core file bfd. */
400 @@ -393,6 +765,9 @@ core_open (char *filename, int from_tty)
401 /* Fetch all registers from core file. */
402 target_fetch_registers (-1);
404 + /* Locate objid section, if present. */
405 + objid_locate (core_bfd, from_tty);
407 /* Add symbols and section mappings for any shared libraries. */
409 catch_errors (solib_add_stub, &from_tty, (char *) 0,
410 @@ -679,8 +1054,26 @@ int coreops_suppress_target;
412 _initialize_corelow (void)
414 + struct cmd_list_element *c;
418 if (!coreops_suppress_target)
419 add_target (&core_ops);
421 + init_object_path ();
423 + c = add_cmd ("objectdirectory", class_files, objectdirectory_command,
424 + "Add directory DIR to beginning of libobjid based search path\n\
425 +for binary files.\n\
426 +DIR can also be $cwd for the current working directory.\n\
427 +With no argument, reset the search path to be empty, the default.",
430 + set_cmd_completer (c, filename_completer);
432 + add_cmd ("objectdirectories", no_class, show_objectdirectories,
433 + "Current search path for libobjid based finding binary files.\n\
434 +$cwd in the path means the current working directory.",
437 diff -u -rup -x testsuite gdb-6.3-orig/gdb/defs.h gdb-6.3/gdb/defs.h
438 --- gdb-6.3-orig/gdb/defs.h 2006-12-28 17:29:07.000000000 +0100
439 +++ gdb-6.3/gdb/defs.h 2006-12-28 18:23:59.000000000 +0100
440 @@ -614,6 +614,11 @@ extern void init_source_path (void);
442 extern void init_last_source_visited (void);
444 +/* From corelow.c */
445 +/* FIXME: init.c based. */
447 +extern void objectdirectory_command (char *dirname, int from_tty);
451 extern void exec_set_section_offsets (bfd_signed_vma text_off,
452 diff -u -rup -x testsuite gdb-6.3-orig/gdb/main.c gdb-6.3/gdb/main.c
453 --- gdb-6.3-orig/gdb/main.c 2006-12-28 17:29:10.000000000 +0100
454 +++ gdb-6.3/gdb/main.c 2006-12-28 20:23:46.000000000 +0100
455 @@ -134,6 +134,13 @@ captured_main (void *data)
456 /* Number of elements of cmdarg used. */
459 + /* Indices of all arguments of --objectdirectory option. */
460 + char **objectdirarg;
461 + /* Allocated size. */
463 + /* Number of elements used. */
466 /* Indices of all arguments of --directory option. */
468 /* Allocated size. */
469 @@ -173,6 +180,9 @@ captured_main (void *data)
471 dirarg = (char **) xmalloc (dirsize * sizeof (*dirarg));
474 + objectdirarg = (char **) xmalloc (objectdirsize * sizeof (*objectdirarg));
478 line = (char *) xmalloc (linesize);
479 @@ -240,7 +250,8 @@ captured_main (void *data)
485 + OPT_OBJECTDIRECTORY
487 static struct option long_options[] =
489 @@ -289,6 +300,7 @@ captured_main (void *data)
490 {"interpreter", required_argument, 0, 'i'},
491 {"i", required_argument, 0, 'i'},
492 {"directory", required_argument, 0, 'd'},
493 + {"objectdirectory", required_argument, 0, OPT_OBJECTDIRECTORY},
494 {"d", required_argument, 0, 'd'},
495 {"cd", required_argument, 0, OPT_CD},
496 {"tty", required_argument, 0, 't'},
497 @@ -457,6 +469,16 @@ extern int gdbtk_test (char *);
501 + case OPT_OBJECTDIRECTORY:
502 + objectdirarg[nobjectdir++] = optarg;
503 + if (nobjectdir >= objectdirsize)
505 + objectdirsize *= 2;
506 + objectdirarg = (char **) xrealloc ((char *) objectdirarg,
508 + * sizeof (*objectdirarg));
513 fprintf_unfiltered (gdb_stderr,
514 @@ -636,6 +658,11 @@ extern int gdbtk_test (char *);
515 catch_command_errors (directory_command, dirarg[i], 0, RETURN_MASK_ALL);
518 + for (i = 0; i < nobjectdir; i++)
519 + catch_command_errors (objectdirectory_command, objectdirarg[i], 0,
521 + xfree (objectdirarg);
525 && strcmp (execarg, symarg) == 0)
526 @@ -845,6 +872,7 @@ Options:\n\n\
527 fputs_unfiltered (_("\
528 --dbx DBX compatibility mode.\n\
529 --directory=DIR Search for source files in DIR.\n\
530 + --objectdirectory=DIR Search for binary files by libobjid in DIR.\n\
531 --epoch Output information used by epoch emacs-GDB interface.\n\
532 --exec=EXECFILE Use EXECFILE as the executable.\n\
533 --fullname Output information used by emacs-GDB interface.\n\
534 diff -u -rup -x testsuite gdb-6.3-orig/gdb/objid.h gdb-6.3/gdb/objid.h
535 --- gdb-6.3-orig/gdb/objid.h 2006-12-29 11:34:47.000000000 +0100
536 +++ gdb-6.3/gdb/objid.h 2006-12-28 21:27:51.000000000 +0100
545 +#define Elf32_Magic 0x0B11D032
546 +#define Elf64_Magic 0x0B11D064
550 + ElfW(Addr) filename;
551 + ElfW(Word) checksum;
552 + } ElfW(LibobjidObj);
558 + ElfW(Addr) self_not; /* == ~self */
559 + /* Total size of all OBJs including this header. */
561 + ElfW(Word) obj_count;
562 + ElfW(LibobjidObj) obj[0];
563 + } ElfW(LibobjidHdr);
566 +#endif /* !OBJID_H */
567 diff -u -rup -x testsuite gdb-6.3-orig/gdb/solib.c gdb-6.3/gdb/solib.c
568 --- gdb-6.3-orig/gdb/solib.c 2006-12-28 17:29:11.000000000 +0100
569 +++ gdb-6.3/gdb/solib.c 2006-12-29 01:37:08.000000000 +0100
570 @@ -73,6 +73,60 @@ static char *solib_search_path = NULL;
572 void add_to_target_sections (int, struct target_ops *, struct so_list *);
574 +struct solib_open_map
576 + struct solib_open_map *next;
580 +static struct solib_open_map *solib_open_map_list;
583 +solib_open_map_find (const char *from)
585 + struct solib_open_map *item;
587 + for (item = solib_open_map_list; item != NULL; item = item->next)
588 + if (strcmp (item->from, from) == 0)
595 +solib_open_map (const char *from, const char *to)
597 + const char *to_old;
598 + struct solib_open_map *item_new;
600 + to_old = solib_open_map_find (from);
601 + if (to_old != NULL && strcmp (to_old, to) != 0)
602 + warning ("Duplicite mapping of `%s' -> `%s' vs. `%s'", from, to_old, to);
603 + if (to_old != NULL)
606 + item_new = xmalloc (sizeof (*item_new));
607 + item_new->from = xstrdup (from);
608 + item_new->to = xstrdup (to);
609 + item_new->next = solib_open_map_list;
610 + solib_open_map_list = item_new;
614 +solib_open_map_reset (void)
616 + while (solib_open_map_list != NULL)
618 + struct solib_open_map *freeing;
620 + freeing = solib_open_map_list;
621 + xfree (freeing->from);
622 + xfree (freeing->to);
623 + solib_open_map_list = freeing->next;
631 @@ -117,6 +171,11 @@ solib_open (char *in_pathname, char **fo
632 char *temp_pathname = NULL;
633 char *p = in_pathname;
634 int solib_absolute_prefix_is_empty;
635 + const char *in_pathname_mapped;
637 + in_pathname_mapped = solib_open_map_find (in_pathname);
638 + if (in_pathname_mapped != NULL)
639 + in_pathname = (char *) in_pathname_mapped;
641 solib_absolute_prefix_is_empty = (solib_absolute_prefix == NULL
642 || *solib_absolute_prefix == 0);
643 @@ -821,6 +880,8 @@ clear_solib (void)
646 TARGET_SO_CLEAR_SOLIB ();
648 + solib_open_map_reset ();
652 diff -u -rup -x testsuite gdb-6.3-orig/gdb/solist.h gdb-6.3/gdb/solist.h
653 --- gdb-6.3-orig/gdb/solist.h 2006-12-28 17:29:07.000000000 +0100
654 +++ gdb-6.3/gdb/solist.h 2006-12-29 00:10:49.000000000 +0100
655 @@ -121,6 +121,8 @@ struct so_list *master_so_list (void);
656 /* Find solib binary file and open it. */
657 extern int solib_open (char *in_pathname, char **found_pathname);
659 +extern void solib_open_map (const char *from, const char *to);
661 /* Add the list of sections in so_list to the target to_sections. */
662 extern void add_to_target_sections (int, struct target_ops *, struct so_list *);
664 diff -u -rup -x testsuite gdb-6.3-orig/gdb/symfile.c gdb-6.3/gdb/symfile.c
665 --- gdb-6.3-orig/gdb/symfile.c 2006-12-28 17:29:10.000000000 +0100
666 +++ gdb-6.3/gdb/symfile.c 2006-12-28 21:59:10.000000000 +0100
667 @@ -973,6 +973,12 @@ symbol_file_add_main (char *args, int fr
668 symbol_file_add_main_1 (args, from_tty, 0);
672 +symbol_file_add_main_userloaded (char *args, int from_tty)
674 + symbol_file_add_main_1 (args, from_tty, OBJF_USERLOADED);
678 symbol_file_add_main_1 (char *args, int from_tty, int flags)
680 diff -u -rup -x testsuite gdb-6.3-orig/gdb/symfile.h gdb-6.3/gdb/symfile.h
681 --- gdb-6.3-orig/gdb/symfile.h 2004-09-08 23:58:19.000000000 +0200
682 +++ gdb-6.3/gdb/symfile.h 2006-12-28 21:59:11.000000000 +0100
683 @@ -310,6 +310,7 @@ extern CORE_ADDR symbol_overlayed_addres
685 /* Load symbols from a file. */
686 extern void symbol_file_add_main (char *args, int from_tty);
687 +extern void symbol_file_add_main_userloaded (char *args, int from_tty);
689 /* Clear GDB symbol tables. */
690 extern void symbol_file_clear (int from_tty);