Numerous small changes and a complete reorganization of solib.c, to support

SVR4 shared libraries in a manner very close to the original SunOS support.
See the ChangeLog for details.
This commit is contained in:
Fred Fish 1991-12-16 20:57:28 +00:00
parent 01d4cbef85
commit f8b76e70b7
6 changed files with 1203 additions and 335 deletions

View File

@ -1,3 +1,47 @@
Mon Dec 16 12:31:46 1991 Fred Fish (fnf at cygnus.com)
* solib.c: Completely reorganized (rewritten) to support
SVR4 shared libraries in a manner very close to the original
SunOS implementation. This support is expected to change and
become more general at some future time. The SVR4 version
does not yet work for attached processes, for example.
* dwarfread.c: Arrange in dwarf_build_psymtabs() for the
relocation address to be valid whether or not symbols are
being read from a shared library or an executable. Use the
relocation address recorded in the psymtab when reading
full symbol tables (in read_ofile_symtab). Ensure that the
relocated address ranges are recorded in partial symtabs.
* elfread.c: Add new function elf_interpreter() to return the
string from the ELF ".interp" section. This is the interpreter
that the kernel tries to run and feed the executable to.
Expand arguments to record_misc_function to include a type arg.
Modify elf_symtab_read() to supply the type arg, and to do symbol
relocations for symbols read in from shared libraries.
* procfs.c: Add new functions proc_base_address() and
proc_address_to_fd(), used by shared library support.
* tm-svr4.h: Add macros to support SVR4 shared libraries.
Definitions for SOLIB_ADD, SOLIB_CREATE_INFERIOR_HOOK,
CLEAR_SOLIB, and DISABLE_UNSETTABLE_BREAK.
Fri Dec 13 20:11:26 1991 John Gilmore (gnu at cygnus.com)
* infrun.c, remote-eb.c, remote-nindy.c, remote-vx.c: Remove
unused START_INFERIOR_HOOK.
* remote-eb.c: Change timeout to 24 seconds (*10 fits in byte)
to account for slow loading from floppies.
(eb_create_inferior): New fn, from eb_start and
nindy_create_inferior.
(eb_close): Only use log_file if nonzero.
(eb_xfer_memory): If not writing, then read!
(eb_read_inferior_memory, eb_write_inferior_memory): Return length.
(eb_kill): A new no-op.
(eb_mourn_inferior): Remove breakpoints, then generically weep.
Fri Dec 13 16:09:23 1991 Fred Fish (fnf at cygnus.com)
* breakpoint.c, findvar.c, infrun.c, putenv.c, stack.c: Fix
@ -5,6 +49,21 @@ Fri Dec 13 16:09:23 1991 Fred Fish (fnf at cygnus.com)
compiler warnings about comparison of integer with pointer, when
NULL is ((void *) 0) rather than just a bare 0.
Wed Dec 11 13:02:58 1991 John Gilmore (gnu at cygnus.com)
* breakpoint.c (breakpoint_re_set_one): Disable each breakpoint
while we reset it, in case of problems. Print breakpoint number
in error messages.
* buildsym.c (read_struct_type): Avoid sun3 compiler bug with
foo[--n].
* source.c (find_source_lines): If getting file mod time fails,
don't warn.
* target.c (target_xfer_memory): If errno is set, return it,
rather than EIO.
Tue Dec 10 04:07:22 1991 K. Richard Pixley (rich at rtl.cygnus.com)
* Makefile.in: infodir belongs in datadir.

View File

@ -535,6 +535,14 @@ DEFUN(dwarf_build_psymtabs,
init_psymbol_list (1024);
}
/* From this point on, we don't need to pass mainline around, so zap
addr to zero if we don't need relocation. */
if (mainline)
{
addr = 0;
}
/* Follow the compilation unit sibling chain, building a partial symbol
table entry for each one. Save enough information about each compilation
unit to locate the full DWARF information later. */
@ -2356,7 +2364,6 @@ SYNOPSIS
DESCRIPTION
OFFSET is a relocation offset which gets added to each symbol (FIXME).
*/
static struct symtab *
@ -2375,6 +2382,7 @@ DEFUN(read_ofile_symtab, (pst),
dbbase = xmalloc (DBLENGTH(pst));
dbroff = DBROFF(pst);
foffset = DBFOFF(pst) + dbroff;
baseaddr = pst -> addr;
if (bfd_seek (abfd, foffset, 0) ||
(bfd_read (dbbase, DBLENGTH(pst), 1, abfd) != DBLENGTH(pst)))
{
@ -2407,7 +2415,7 @@ DEFUN(read_ofile_symtab, (pst),
make_cleanup (free, lnbase);
}
process_dies (dbbase, dbbase + DBLENGTH(pst), pst->objfile);
process_dies (dbbase, dbbase + DBLENGTH(pst), pst -> objfile);
do_cleanups (back_to);
return (symtab_list);
}
@ -2467,7 +2475,6 @@ DEFUN(psymtab_to_symtab_1,
if (DBLENGTH(pst)) /* Otherwise it's a dummy */
{
/* Init stuff necessary for reading in symbols */
pst -> symtab = read_ofile_symtab (pst);
if (info_verbose)
{
@ -2958,7 +2965,8 @@ DEFUN(scan_compilation_units,
culength = nextdie - thisdie;
curlnoffset = di.has_at_stmt_list ? lnoffset + di.at_stmt_list : 0;
pst = start_psymtab (objfile, addr, di.at_name,
di.at_low_pc, di.at_high_pc,
di.at_low_pc + addr,
di.at_high_pc + addr,
dbfoff, curoff, culength, curlnoffset,
global_psymbols.next,
static_psymbols.next);

View File

@ -93,6 +93,32 @@ DEFUN(elf_locate_sections, (abfd, sectp, ei),
}
}
char *
DEFUN(elf_interpreter, (abfd),
bfd *abfd)
{
sec_ptr interp_sec;
unsigned size;
char *interp = NULL;
interp_sec = bfd_get_section_by_name (abfd, ".interp");
if (interp_sec)
{
size = bfd_section_size (abfd, interp_sec);
interp = alloca (size);
if (bfd_get_section_contents (abfd, interp_sec, interp, (file_ptr)0,
size))
{
interp = savestring (interp, size - 1);
}
else
{
interp = NULL;
}
}
return (interp);
}
/*
LOCAL FUNCTION
@ -117,16 +143,37 @@ NOTES
*/
static void
DEFUN(record_misc_function, (name, address), char *name AND CORE_ADDR address)
DEFUN(record_misc_function, (name, address, mf_type),
char *name AND CORE_ADDR address AND enum misc_function_type mf_type)
{
prim_record_misc_function (obsavestring (name, strlen (name)), address,
mf_unknown);
mf_type);
}
/*
LOCAL FUNCTION
elf_symtab_read -- read the symbol table of an ELF file
SYNOPSIS
void elf_symtab_read (bfd *abfd, CORE_ADDR addr, int mainline)
DESCRIPTION
Given an open bfd, a base address to relocate symbols to, and a
flag that specifies whether or not this bfd is for an executable
or not (may be shared library for example), add all the global
function and data symbols to the miscellaneous function vector.
*/
static void
DEFUN (elf_symtab_read, (abfd, addr),
DEFUN (elf_symtab_read, (abfd, addr, mainline),
bfd *abfd AND
CORE_ADDR addr)
CORE_ADDR addr AND
int mainline)
{
unsigned int storage_needed;
asymbol *sym;
@ -134,6 +181,8 @@ DEFUN (elf_symtab_read, (abfd, addr),
unsigned int number_of_symbols;
unsigned int i;
struct cleanup *back_to;
CORE_ADDR symaddr;
enum misc_function_type mf_type;
storage_needed = get_symtab_upper_bound (abfd);
@ -151,7 +200,28 @@ DEFUN (elf_symtab_read, (abfd, addr),
if (sym -> flags & BSF_GLOBAL
&& ((sym -> section != NULL) || (sym -> flags & BSF_ABSOLUTE)))
{
record_misc_function ((char *) sym -> name, sym -> value);
symaddr = sym -> value;
if (!mainline)
{
/* Relocate all symbols by base address */
symaddr += addr;
}
/* For non-absolute symbols, use the type of the section
they are relative to, to intuit text/data. Bfd provides
no way of figuring this out for absolute symbols. */
if (sym -> section && (sym -> section -> flags & SEC_CODE))
{
mf_type = mf_text;
}
else if (sym -> section && (sym -> section -> flags & SEC_DATA))
{
mf_type = mf_data;
}
else
{
mf_type = mf_unknown;
}
record_misc_function ((char *) sym -> name, symaddr, mf_type);
}
}
do_cleanups (back_to);
@ -199,7 +269,7 @@ DEFUN(elf_symfile_read, (sf, addr, mainline),
/* Process the normal ELF symbol table first. */
elf_symtab_read (abfd, addr);
elf_symtab_read (abfd, addr, mainline);
/* Now process the DWARF debugging information, which is contained in
special ELF sections. We first have to find them... */
@ -208,7 +278,6 @@ DEFUN(elf_symfile_read, (sf, addr, mainline),
bfd_map_over_sections (abfd, elf_locate_sections, &ei);
if (ei.dboffset && ei.lnoffset)
{
addr = 0; /* FIXME: force address base to zero for now */
dwarf_build_psymtabs (fileno ((FILE *)(abfd -> iostream)),
bfd_get_filename (abfd),
addr, mainline,

View File

@ -451,6 +451,93 @@ DEFUN_VOID(proc_set_exec_trap)
}
}
/*
GLOBAL FUNCTION
proc_base_address -- find base address for segment containing address
SYNOPSIS
CORE_ADDR proc_base_address (CORE_ADDR addr)
DESCRIPTION
Given an address of a location in the inferior, find and return
the base address of the mapped segment containing that address.
This is used for example, by the shared library support code,
where we have the pc value for some location in the shared library
where we are stopped, and need to know the base address of the
segment containing that address.
*/
CORE_ADDR
DEFUN(proc_base_address, (addr),
CORE_ADDR addr)
{
int nmap;
struct prmap *prmaps;
struct prmap *prmap;
CORE_ADDR baseaddr = 0;
if (ioctl (pi.fd, PIOCNMAP, &nmap) == 0)
{
prmaps = alloca ((nmap + 1) * sizeof (*prmaps));
if (ioctl (pi.fd, PIOCMAP, prmaps) == 0)
{
for (prmap = prmaps; prmap -> pr_size; ++prmap)
{
if ((prmap -> pr_vaddr <= (caddr_t) addr) &&
(prmap -> pr_vaddr + prmap -> pr_size > (caddr_t) addr))
{
baseaddr = (CORE_ADDR) prmap -> pr_vaddr;
break;
}
}
}
}
return (baseaddr);
}
/*
GLOBAL_FUNCTION
proc_address_to_fd -- return open fd for file mapped to address
SYNOPSIS
int proc_address_to_fd (CORE_ADDR addr)
DESCRIPTION
Given an address in the current inferior's address space, use the
/proc interface to find an open file descriptor for the file that
this address was mapped in from. Return -1 if there is no current
inferior. Print a warning message if there is an inferior but
the address corresponds to no file (IE a bogus address).
*/
int
DEFUN(proc_address_to_fd, (addr),
CORE_ADDR addr)
{
int fd = -1;
if (pi.valid)
{
if ((fd = ioctl (pi.fd, PIOCOPENM, (caddr_t *) &addr)) < 0)
{
print_sys_errmsg (pi.pathname, errno);
warning ("can't find mapped file for address 0x%x", addr);
}
}
return (fd);
}
#ifdef ATTACH_DETACH

File diff suppressed because it is too large Load Diff

View File

@ -18,4 +18,20 @@ You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
/* Currently empty */
/* Support for SVR4 shared libraries. */
#define CLEAR_SOLIB clear_solib
extern void clear_solib (); /* solib.c */
#define SOLIB_ADD(filename, from_tty, targ) solib_add (filename, from_tty, targ)
extern void solib_add (); /* solib.c */
#define SOLIB_CREATE_INFERIOR_HOOK solib_create_inferior_hook
extern void solib_create_inferior_hook(); /* solib.c */
/* If we can't set a breakpoint, and it's in a shared library, just
disable it. */
#define DISABLE_UNSETTABLE_BREAK(addr) solib_address(addr)
extern int solib_address (); /* solib.c */