diff options
-rw-r--r-- | gdb/ChangeLog | 7 | ||||
-rw-r--r-- | gdb/solib.c | 147 | ||||
-rw-r--r-- | gdb/solist.h | 3 |
3 files changed, 110 insertions, 47 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 0de7554..bfd70a6 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,5 +1,12 @@ 2015-04-17 Gary Benson <gbenson@redhat.com> + * solist.h (exec_file_find): New declaration. + * solib.c (solib_find_1): New function, factored out from... + (solib_find): ...here. + (exec_file_find): New function. + +2015-04-17 Gary Benson <gbenson@redhat.com> + * gdbcore.h (exec_file_locate_attach): New declaration. * exec.c (exec_file_locate_attach): New function, factored out from... diff --git a/gdb/solib.c b/gdb/solib.c index 31298a7..2466235 100644 --- a/gdb/solib.c +++ b/gdb/solib.c @@ -112,13 +112,13 @@ show_solib_search_path (struct ui_file *file, int from_tty, # define DOS_BASED_FILE_SYSTEM 0 #endif -/* Returns the full pathname of the shared library file, or NULL if - not found. (The pathname is malloc'ed; it needs to be freed by the - caller.) *FD is set to either -1 or an open file handle for the - library. +/* Return the full pathname of a binary file (the main executable + or a shared library file), or NULL if not found. The returned + pathname is malloc'ed and must be freed by the caller. *FD is + set to either -1 or an open file handle for the binary file. Global variable GDB_SYSROOT is used as a prefix directory - to search for shared libraries if they have an absolute path. + to search for binary files if they have an absolute path. If GDB_SYSROOT starts with "target:" and target filesystem is the local filesystem then the "target:" prefix will be stripped before the search starts. This ensures that the @@ -128,58 +128,36 @@ show_solib_search_path (struct ui_file *file, int from_tty, Global variable SOLIB_SEARCH_PATH is used as a prefix directory (or set of directories, as in LD_LIBRARY_PATH) to search for all shared libraries if not found in either the sysroot (if set) or - the local filesystem. + the local filesystem. SOLIB_SEARCH_PATH is not used when searching + for the main executable. Search algorithm: * If a sysroot is set and path is absolute: * Search for sysroot/path. * else * Look for it literally (unmodified). - * Look in SOLIB_SEARCH_PATH. - * If available, use target defined search function. + * If IS_SOLIB is non-zero: + * Look in SOLIB_SEARCH_PATH. + * If available, use target defined search function. * If NO sysroot is set, perform the following two searches: * Look in inferior's $PATH. - * Look in inferior's $LD_LIBRARY_PATH. + * If IS_SOLIB is non-zero: + * Look in inferior's $LD_LIBRARY_PATH. * * The last check avoids doing this search when targetting remote * machines since a sysroot will almost always be set. */ -char * -solib_find (char *in_pathname, int *fd) +static char * +solib_find_1 (char *in_pathname, int *fd, int is_solib) { const struct target_so_ops *ops = solib_ops (target_gdbarch ()); int found_file = -1; char *temp_pathname = NULL; - const char *solib_symbols_extension - = gdbarch_solib_symbols_extension (target_gdbarch ()); const char *fskind = effective_target_file_system_kind (); struct cleanup *old_chain = make_cleanup (null_cleanup, NULL); char *sysroot = gdb_sysroot; - /* If solib_symbols_extension is set, replace the file's - extension. */ - if (solib_symbols_extension) - { - char *p = in_pathname + strlen (in_pathname); - - while (p > in_pathname && *p != '.') - p--; - - if (*p == '.') - { - char *new_pathname; - - new_pathname = alloca (p - in_pathname + 1 - + strlen (solib_symbols_extension) + 1); - memcpy (new_pathname, in_pathname, p - in_pathname + 1); - strcpy (new_pathname + (p - in_pathname) + 1, - solib_symbols_extension); - - in_pathname = new_pathname; - } - } - if (sysroot != NULL) { /* If the absolute prefix starts with "target:" but the @@ -351,23 +329,26 @@ solib_find (char *in_pathname, int *fd) in_pathname++; } - /* If not found, search the solib_search_path (if any). */ - if (found_file < 0 && solib_search_path != NULL) + /* If not found, and we're looking for a solib, search the + solib_search_path (if any). */ + if (is_solib && found_file < 0 && solib_search_path != NULL) found_file = openp (solib_search_path, OPF_TRY_CWD_FIRST | OPF_RETURN_REALPATH, in_pathname, O_RDONLY | O_BINARY, &temp_pathname); - /* If not found, next search the solib_search_path (if any) for the basename - only (ignoring the path). This is to allow reading solibs from a path - that differs from the opened path. */ - if (found_file < 0 && solib_search_path != NULL) + /* If not found, and we're looking for a solib, next search the + solib_search_path (if any) for the basename only (ignoring the + path). This is to allow reading solibs from a path that differs + from the opened path. */ + if (is_solib && found_file < 0 && solib_search_path != NULL) found_file = openp (solib_search_path, OPF_TRY_CWD_FIRST | OPF_RETURN_REALPATH, target_lbasename (fskind, in_pathname), O_RDONLY | O_BINARY, &temp_pathname); - /* If not found, try to use target supplied solib search method. */ - if (found_file < 0 && ops->find_and_open_solib) + /* If not found, and we're looking for a solib, try to use target + supplied solib search method. */ + if (is_solib && found_file < 0 && ops->find_and_open_solib) found_file = ops->find_and_open_solib (in_pathname, O_RDONLY | O_BINARY, &temp_pathname); @@ -378,9 +359,9 @@ solib_find (char *in_pathname, int *fd) OPF_TRY_CWD_FIRST | OPF_RETURN_REALPATH, in_pathname, O_RDONLY | O_BINARY, &temp_pathname); - /* If not found, next search the inferior's $LD_LIBRARY_PATH - environment variable. */ - if (found_file < 0 && sysroot == NULL) + /* If not found, and we're looking for a solib, next search the + inferior's $LD_LIBRARY_PATH environment variable. */ + if (is_solib && found_file < 0 && sysroot == NULL) found_file = openp (get_in_environ (current_inferior ()->environment, "LD_LIBRARY_PATH"), OPF_TRY_CWD_FIRST | OPF_RETURN_REALPATH, in_pathname, @@ -390,6 +371,78 @@ solib_find (char *in_pathname, int *fd) return temp_pathname; } +/* Return the full pathname of the main executable, or NULL if not + found. The returned pathname is malloc'ed and must be freed by + the caller. *FD is set to either -1 or an open file handle for + the main executable. + + The search algorithm used is described in solib_find_1's comment + above. */ + +char * +exec_file_find (char *in_pathname, int *fd) +{ + char *result = solib_find_1 (in_pathname, fd, 0); + + if (result == NULL) + { + const char *fskind = effective_target_file_system_kind (); + + if (fskind == file_system_kind_dos_based) + { + char *new_pathname; + + new_pathname = alloca (strlen (in_pathname) + 5); + strcpy (new_pathname, in_pathname); + strcat (new_pathname, ".exe"); + + result = solib_find_1 (new_pathname, fd, 0); + } + } + + return result; +} + +/* Return the full pathname of a shared library file, or NULL if not + found. The returned pathname is malloc'ed and must be freed by + the caller. *FD is set to either -1 or an open file handle for + the shared library. + + The search algorithm used is described in solib_find_1's comment + above. */ + +char * +solib_find (char *in_pathname, int *fd) +{ + const char *solib_symbols_extension + = gdbarch_solib_symbols_extension (target_gdbarch ()); + + /* If solib_symbols_extension is set, replace the file's + extension. */ + if (solib_symbols_extension != NULL) + { + char *p = in_pathname + strlen (in_pathname); + + while (p > in_pathname && *p != '.') + p--; + + if (*p == '.') + { + char *new_pathname; + + new_pathname = alloca (p - in_pathname + 1 + + strlen (solib_symbols_extension) + 1); + memcpy (new_pathname, in_pathname, p - in_pathname + 1); + strcpy (new_pathname + (p - in_pathname) + 1, + solib_symbols_extension); + + in_pathname = new_pathname; + } + } + + return solib_find_1 (in_pathname, fd, 1); +} + /* Open and return a BFD for the shared library PATHNAME. If FD is not -1, it is used as file handle to open the file. Throws an error if the file could not be opened. Handles both local and remote file access. diff --git a/gdb/solist.h b/gdb/solist.h index 148bec1..7021f5c 100644 --- a/gdb/solist.h +++ b/gdb/solist.h @@ -176,6 +176,9 @@ void free_so (struct so_list *so); /* Return address of first so_list entry in master shared object list. */ struct so_list *master_so_list (void); +/* Find main executable binary file. */ +extern char *exec_file_find (char *in_pathname, int *fd); + /* Find shared library binary file. */ extern char *solib_find (char *in_pathname, int *fd); |