From: Jeff Law Date: Mon, 7 Nov 1994 07:51:47 +0000 (+0000) Subject: * Beginnings of SOM shared library support. Breakpoints and X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=bb140953e4bab8026ff4c51f017755acbb3b253d;p=binutils-gdb.git * Beginnings of SOM shared library support. Breakpoints and single frame backtracing within the library only. Only works when using the HPUX 9 dynamic linker. More functionality to be added soon. * somsolib.c, somsolib.h: New files. * Makefile.in (HFILES_NO_SRCDIR): Add somsolib.h (ALLDEPFILES): Add somsolib.c. (somsolib.o): Add some dependencies. * mpw-make.in (HFILES_NO_SRCDIR): Add somsolib.h (ALLDEPFILES): Add somsolib.c. (somsolib.o): Add some dependencies. * somread.c (som_symtab_read): Accept multiple section offsets. All callers changed. Adjust all text symbols with the first section offset. * symfile.c (find_lowest_section): Enable this function. Add some tie-breaking logic when sections have the same vma. (syms_from_objfile): Use find_lowest_section rather than looking for ".text" by name. Relax warning to only warn if the lowest section is not a code section. * config/pa/{hppabsd.mh, hppahpux.mh} (NATDEPFILES): Add somsolib.o * config/pa/{nm-hppab.h, nm-hppah.h}: Include somsolib.h. --- diff --git a/gdb/.Sanitize b/gdb/.Sanitize index 7f457365ba0..ca52bf7ff2a 100644 --- a/gdb/.Sanitize +++ b/gdb/.Sanitize @@ -271,6 +271,8 @@ signals.h solib.c solib.h somread.c +somsolib.c +somsolib.h source.c sp64-tdep.c sparc-nat.c diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 6604be013a9..c2e961405de 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,25 @@ +Mon Nov 7 00:27:16 1994 Jeff Law (law@snake.cs.utah.edu) + + * Beginnings of SOM shared library support. Breakpoints and + single frame backtracing within the library only. Only works when + using the HPUX 9 dynamic linker. More functionality to be added + soon. + + * somsolib.c, somsolib.h: New files. + * Makefile.in (HFILES_NO_SRCDIR): Add somsolib.h + (ALLDEPFILES): Add somsolib.c. + (somsolib.o): Add some dependencies. + * somread.c (som_symtab_read): Accept multiple section offsets. + All callers changed. Adjust all text symbols with the first + section offset. + * symfile.c (find_lowest_section): Enable this function. Add some + tie-breaking logic when sections have the same vma. + (syms_from_objfile): Use find_lowest_section rather than looking + for ".text" by name. Relax warning to only warn if the lowest + section is not a code section. + * config/pa/{hppabsd.mh, hppahpux.mh} (NATDEPFILES): Add somsolib.o + * config/pa/{nm-hppab.h, nm-hppah.h}: Include somsolib.h. + Sun Nov 6 12:54:54 1994 Jeff Law (law@snake.cs.utah.edu) * partial-stab.h (N_TEXT): Put back GDB_TARGET_IS_HPPA kludge, diff --git a/gdb/ChangeLog.mpw b/gdb/ChangeLog.mpw index 4420fe4391f..e716e26972c 100644 --- a/gdb/ChangeLog.mpw +++ b/gdb/ChangeLog.mpw @@ -1,3 +1,9 @@ +Mon Nov 7 00:46:22 1994 Jeff Law (law@snake.cs.utah.edu) + + * mpw-make.in (HFILES_NO_SRCDIR): Add somsolib.h + (ALLDEPFILES): Add somsolib.c. + (somsolib.o): Add some dependencies. + Mon Sep 12 17:44:58 1994 Stan Shebs (shebs@andros.cygnus.com) * mpw-config.in: Use nm-empty.h if host is not target. diff --git a/gdb/config/pa/hppabsd.mh b/gdb/config/pa/hppabsd.mh index cbb6f8bbb2b..161292d65e3 100644 --- a/gdb/config/pa/hppabsd.mh +++ b/gdb/config/pa/hppabsd.mh @@ -6,4 +6,4 @@ HPREAD=hpread.o XDEPFILES= XM_FILE= xm-hppab.h NAT_FILE= nm-hppab.h -NATDEPFILES= hppab-nat.o coredep.o corelow.o inftarg.o fork-child.o somread.o infptrace.o $(HPREAD) +NATDEPFILES= hppab-nat.o coredep.o corelow.o inftarg.o fork-child.o somread.o infptrace.o $(HPREAD) somsolib.o diff --git a/gdb/config/pa/hppahpux.mh b/gdb/config/pa/hppahpux.mh index 6cfa8ed9845..dff59ab37dc 100644 --- a/gdb/config/pa/hppahpux.mh +++ b/gdb/config/pa/hppahpux.mh @@ -10,6 +10,6 @@ XM_FILE= xm-hppah.h XDEPFILES= ser-tcp.o NAT_FILE= nm-hppah.h -NATDEPFILES= hppah-nat.o coredep.o corelow.o inftarg.o fork-child.o somread.o infptrace.o $(HPREAD) +NATDEPFILES= hppah-nat.o coredep.o corelow.o inftarg.o fork-child.o somread.o infptrace.o $(HPREAD) somsolib.o HOST_IPC=-DBSD_IPC -DPOSIX_WAIT diff --git a/gdb/config/pa/nm-hppab.h b/gdb/config/pa/nm-hppab.h index 458165862c9..421dfd78021 100644 --- a/gdb/config/pa/nm-hppab.h +++ b/gdb/config/pa/nm-hppab.h @@ -17,6 +17,8 @@ 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. */ +#include "somsolib.h" + #define U_REGS_OFFSET 0 #define KERNEL_U_ADDR 0 diff --git a/gdb/config/pa/nm-hppah.h b/gdb/config/pa/nm-hppah.h index fdbc17eb4c7..f10e5048dbe 100644 --- a/gdb/config/pa/nm-hppah.h +++ b/gdb/config/pa/nm-hppah.h @@ -17,6 +17,8 @@ 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. */ +#include "somsolib.h" + #define U_REGS_OFFSET 0 #define KERNEL_U_ADDR 0 diff --git a/gdb/mpw-make.in b/gdb/mpw-make.in index 94a667e1938..73568ad91b7 100644 --- a/gdb/mpw-make.in +++ b/gdb/mpw-make.in @@ -345,7 +345,8 @@ ALLDEPFILES = "{s}"29k-share:udi:udip2soc.c "{s}"29k-share:udi:udr.c \Option-d "{s}"nindy-share:Onindy.c "{s}"nindy-share:nindy.c \Option-d "{s}"nindy-share:ttyflush.c "{s}"nindy-tdep.c \Option-d "{s}"ns32k-pinsn.c "{s}"ns32km3-nat.c "{s}"osfsolib.c \Option-d - "{s}"somread.c "{s}"procfs.c "{s}"pyr-pinsn.c "{s}"pyr-tdep.c "{s}"pyr-xdep.c \Option-d + "{s}"somread.c "{s}"somsolib.c \ + "{s}"procfs.c "{s}"pyr-pinsn.c "{s}"pyr-tdep.c "{s}"pyr-xdep.c \Option-d "{s}"remote-adapt.c "{s}"remote-bug.c "{s}"remote-e7000.c "{s}"remote-eb.c "{s}"remote-es.c \Option-d "{s}"remote-hms.c "{s}"remote-mips.c \Option-d "{s}"remote-mm.c "{s}"remote-mon.c "{s}"remote-nindy.c "{s}"remote-sim.c \Option-d @@ -606,7 +607,7 @@ HFILES_NO_SRCDIR = "{s}"buildsym.h "{s}"call-cmds.h "{s}"coff-solib.h "{s}"defs. "{s}"vx-share:dbgRpcLib.h "{s}"vx-share:ptrace.h "{s}"vx-share:vxTypes.h \Option-d "{s}"vx-share:vxWorks.h "{s}"vx-share:wait.h "{s}"vx-share:xdr_ld.h \Option-d "{s}"vx-share:xdr_ptrace.h "{s}"vx-share:xdr_rdb.h "{s}"thread.h \Option-d - "{s}"dcache.h "{s}"remote-utils.h "{s}"remote-sim.h + "{s}"dcache.h "{s}"remote-utils.h "{s}"remote-sim.h "{s}"somsolib.h # Header files that already have srcdir in them. @@ -1364,6 +1365,8 @@ MAKEOVERRIDES= "{o}"somread.c.o \Option-f "{s}"somread.c {bfd_h} "{s}"buildsym.h "{s}"complaints.h {defs_h} \Option-d "{s}"gdb-stabs.h "{s}"objfiles.h "{s}"symfile.h {symtab_h} +"{o}"somsolib.c.o \Option-f "{s}"somsolib.c {defs_h} + "{o}"parse.c.o \Option-f "{s}"parse.c {command_h} {defs_h} {expression_h} {frame_h} \Option-d {gdbtypes_h} "{s}"language.h "{s}"parser-defs.h {symtab_h} {value_h} diff --git a/gdb/somread.c b/gdb/somread.c index 48ea12404e7..35def2254ab 100644 --- a/gdb/somread.c +++ b/gdb/somread.c @@ -49,7 +49,8 @@ static void som_symfile_finish PARAMS ((struct objfile *)); static void -som_symtab_read PARAMS ((bfd *, CORE_ADDR, struct objfile *)); +som_symtab_read PARAMS ((bfd *, struct objfile *, + struct section_offsets *)); static struct section_offsets * som_symfile_offsets PARAMS ((struct objfile *, CORE_ADDR)); @@ -78,8 +79,8 @@ LOCAL FUNCTION SYNOPSIS - void som_symtab_read (bfd *abfd, CORE_ADDR addr, - struct objfile *objfile) + void som_symtab_read (bfd *abfd, struct objfile *objfile, + struct section_offsets *section_offsets) DESCRIPTION @@ -90,10 +91,10 @@ DESCRIPTION */ static void -som_symtab_read (abfd, addr, objfile) +som_symtab_read (abfd, objfile, section_offsets) bfd *abfd; - CORE_ADDR addr; struct objfile *objfile; + struct section_offsets *section_offsets; { unsigned int number_of_symbols; int val, dynamic; @@ -102,6 +103,11 @@ som_symtab_read (abfd, addr, objfile) struct symbol_dictionary_record *buf, *bufp, *endbufp; char *symname; CONST int symsize = sizeof (struct symbol_dictionary_record); + CORE_ADDR text_offset; + + + /* FIXME. Data stuff needs dynamic relocation too! */ + text_offset = ANOFFSET (section_offsets, 0); number_of_symbols = bfd_get_symcount (abfd); @@ -152,6 +158,7 @@ som_symtab_read (abfd, addr, objfile) case ST_MILLICODE: symname = bufp->name.n_strx + stringtab; ms_type = mst_text; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -166,6 +173,7 @@ som_symtab_read (abfd, addr, objfile) ms_type = mst_solib_trampoline; else ms_type = mst_text; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -174,6 +182,7 @@ som_symtab_read (abfd, addr, objfile) case ST_STUB: symname = bufp->name.n_strx + stringtab; ms_type = mst_solib_trampoline; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -202,6 +211,7 @@ som_symtab_read (abfd, addr, objfile) case ST_CODE: symname = bufp->name.n_strx + stringtab; ms_type = mst_file_text; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -227,6 +237,7 @@ som_symtab_read (abfd, addr, objfile) case ST_MILLICODE: symname = bufp->name.n_strx + stringtab; ms_type = mst_file_text; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -241,6 +252,7 @@ som_symtab_read (abfd, addr, objfile) ms_type = mst_solib_trampoline; else ms_type = mst_file_text; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -249,6 +261,7 @@ som_symtab_read (abfd, addr, objfile) case ST_STUB: symname = bufp->name.n_strx + stringtab; ms_type = mst_solib_trampoline; + bufp->symbol_value += text_offset; #ifdef SMASH_TEXT_ADDRESS SMASH_TEXT_ADDRESS (bufp->symbol_value); #endif @@ -316,18 +329,13 @@ som_symfile_read (objfile, section_offsets, mainline) { bfd *abfd = objfile->obfd; struct cleanup *back_to; - CORE_ADDR offset; init_minimal_symbol_collection (); back_to = make_cleanup (discard_minimal_symbols, 0); - /* FIXME, should take a section_offsets param, not just an offset. */ - - offset = ANOFFSET (section_offsets, 0); - /* Process the normal SOM symbol table first. */ - som_symtab_read (abfd, offset, objfile); + som_symtab_read (abfd, objfile, section_offsets); /* Now read information from the stabs debug sections. */ stabsect_build_psymtabs (objfile, section_offsets, mainline, diff --git a/gdb/somsolib.c b/gdb/somsolib.c new file mode 100644 index 00000000000..67d12ab8fb4 --- /dev/null +++ b/gdb/somsolib.c @@ -0,0 +1,319 @@ +/* Handle HP SOM shared libraries for GDB, the GNU Debugger. + Copyright 1993 Free Software Foundation, Inc. + +This file is part of GDB. + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +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. + +Written by the Center for Software Science at the Univerity of Utah +and by Cygnus Support. */ + + +#include "defs.h" + +#include "frame.h" +#include "bfd.h" +#include "som.h" +#include "libhppa.h" +#include "gdbcore.h" +#include "symtab.h" +#include "breakpoint.h" +#include "symfile.h" +#include "objfiles.h" +#include "inferior.h" + +/* We don't currently use this structure, but it isn't documented anywhere, + and we'll likely need it in som_solib_add as more shared library support + is added. */ + +struct som_solib_mapped_entry +{ + /* The name of the library. */ + char *name; + + /* Version of this structure (it is expected to change again in hpux10. */ + unsigned char struct_version; + + /* Binding mode for this library. */ + unsigned char bind_mode; + + /* Version of this library. */ + short library_version; + + /* Start of text address, link-time text location, end of text address. */ + CORE_ADDR text_addr; + CORE_ADDR text_link_addr; + CORE_ADDR text_end; + + /* Start of data, start of bss and end of data. */ + CORE_ADDR data_start; + CORE_ADDR bss_start; + CORE_ADDR data_end; + + /* Value of linkage pointer (%r19). */ + CORE_ADDR got_value; + + /* Next entry. */ + struct som_solib_mapped_entry *next; + + /* There are other fields, but I don't have information as to what is + contained in them. */ +}; + +/* Add symbols from shared libraries into the symtab list. */ + +void +som_solib_add (arg_string, from_tty, target) + char *arg_string; + int from_tty; + struct target_ops *target; +{ + struct minimal_symbol *msymbol; + CORE_ADDR addr; + int status; + char buf[4]; + + msymbol = lookup_minimal_symbol ("__dld_list", (struct objfile *) NULL); + if (!msymbol) + { + /* Older crt0.o files (hpux8) don't have __dld_list as a symbol, + but the data is still available if you know where to look. */ + msymbol = lookup_minimal_symbol ("__dld_flags", (struct objfile *)NULL); + if (!msymbol) + { + error ("Unable to find dynamic library list.\n"); + return; + } + addr = SYMBOL_VALUE_ADDRESS (msymbol) - 8; + } + else + addr = SYMBOL_VALUE_ADDRESS (msymbol); + + status = target_read_memory (addr, buf, 4); + if (status != 0) + { + error ("Unable to find dynamic library list.\n"); + return; + } + + addr = extract_unsigned_integer (buf, 4); + + /* If addr is zero, then we're using an old dynamic loader which + doesn't maintain __dld_list. We'll have to use a completely + different approach to get shared library information. */ + if (addr == 0) + goto old_dld; + + /* Using the information in __dld_list is the preferred method + to get at shared library information. It doesn't depend on + any functions in /usr/lib/end.o and has a chance of working + with hpux10 when it is released. */ + status = target_read_memory (addr, buf, 4); + if (status != 0) + { + error ("Unable to find dynamic library list.\n"); + return; + } + + /* addr now holds the address of the first entry in the dynamic + library list. */ + addr = extract_unsigned_integer (buf, 4); + + /* Now that we have a pointer to the dynamic library list, walk + through it and add the symbols for each library. + + Skip the first entry since it's our executable. */ + status = target_read_memory (addr + 36, buf, 4); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + addr = extract_unsigned_integer (buf, 4); + + while (1) + { + CORE_ADDR name_addr, text_addr; + unsigned int name_len; + char *name; + if (addr == 0) + break; + + /* Get a pointer to the name of this library. */ + status = target_read_memory (addr, buf, 4); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + name_addr = extract_unsigned_integer (buf, 4); + name_len = 0; + while (1) + { + target_read_memory (name_addr + name_len, buf, 1); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + name_len++; + if (*buf == '\0') + break; + } + name = alloca (name_len); + status = target_read_memory (name_addr, name, name_len); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + name = obsavestring (name, name_len - 1, + &symfile_objfile->symbol_obstack); + + status = target_read_memory (addr + 8, buf, 4); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + text_addr = extract_unsigned_integer (buf, 4); + + /* OK, we've got everything we need. Tell GDB about it. */ + symbol_file_add (name, from_tty, text_addr, 0, 0, 0); + + /* Get address of the next record. */ + status = target_read_memory (addr + 36, buf, 4); + if (status != 0) + { + error ("Error while reading dynamic library list.\n"); + return; + } + addr = extract_unsigned_integer (buf, 4); + } + + /* Getting new symbols may change our opinion about what is + frameless. */ + reinit_frame_cache (); + return; + +old_dld: + error ("Debugging dynamic executables loaded via the hpux8 dld.sl is not supported.\n"); + return; +} + +/* This hook gets called just before the first instruction in the + inferior process is executed. + + This is our opportunity to set magic flags in the inferior so + that GDB can be notified when a shared library is mapped in and + to tell the dynamic linker that a private copy of the library is + needed (so GDB can set breakpoints in the library). + + __dld_flags is the location of the magic flags; as of this implementation + there are 3 flags of interest: + + bit 0 when set indicates that private copies of the libraries are needed + bit 1 when set indicates that the callback hook routine is valid + bit 2 when set indicates that the dynamic linker should maintain the + __dld_list structure when loading/unloading libraries. + + Note that shared libraries are not mapped in at this time, so we have + run the inferior until the libraries are mapped in. Typically this + means running until the "_start" is called. */ + +void +som_solib_create_inferior_hook() +{ + struct minimal_symbol *msymbol; + asection *shlib_info; + unsigned int dld_flags, status; + char shadow_contents[BREAKPOINT_MAX], buf[4]; + CORE_ADDR anaddr; + + /* First see if the objfile was dynamically linked. */ + shlib_info = bfd_get_section_by_name (symfile_objfile->obfd, "$SHLIB_INFO$"); + if (!shlib_info) + return; + + /* It's got a $SHLIB_INFO$ section, make sure it's not empty. */ + if (bfd_section_size (symfile_objfile->obfd, shlib_info) == 0) + return; + + /* Get the address of __dld_flags, if no such symbol exists, then we can + not debug the shared code. */ + msymbol = lookup_minimal_symbol ("__dld_flags", (struct objfile *) NULL); + if (msymbol == NULL) + { + error ("Unable to find __dld_flags symbol in object file.\n"); + return; + } + + anaddr = SYMBOL_VALUE_ADDRESS (msymbol); + /* Read the current contents. */ + status = target_read_memory (anaddr, buf, 4); + if (status != 0) + { + error ("Unable to read __dld_flags\n"); + return; + } + dld_flags = extract_unsigned_integer (buf, 4); + + /* Turn on the flags we care about. */ + dld_flags |= 0x5; + store_unsigned_integer (buf, 4, dld_flags); + status = target_write_memory (anaddr, buf, 4); + if (status != 0) + { + error ("Unable to write __dld_flags\n"); + return; + } + + /* Now find the address of _start and set a breakpoint there. */ + msymbol = lookup_minimal_symbol ("_start", symfile_objfile); + if (msymbol == NULL) + { + error ("Unable to find _start symbol in object file.\n"); + return; + } + + anaddr = SYMBOL_VALUE_ADDRESS (msymbol); + if (target_insert_breakpoint (anaddr, shadow_contents)) + { + error ("Unable to set breakpoint at _start.\n"); + return; + } + + /* Start the process again and wait for it to hit our breakpoint. */ + clear_proceed_status (); + stop_soon_quietly = 1; + stop_signal = TARGET_SIGNAL_0; + do + { + target_resume (-1, 0, stop_signal); + wait_for_inferior (); + } + while (stop_signal != TARGET_SIGNAL_TRAP); + stop_soon_quietly = 0; + + /* All the libraries should be mapped in now. Remove our breakpoint and + read in the symbol tables from the shared libraries. */ + if (target_remove_breakpoint (anaddr, shadow_contents)) + { + error ("Unable to remove breakpoint at _start.\n"); + return; + } + + som_solib_add ((char *) 0, 0, (struct target_ops *) 0); +} diff --git a/gdb/somsolib.h b/gdb/somsolib.h new file mode 100644 index 00000000000..f6b01157668 --- /dev/null +++ b/gdb/somsolib.h @@ -0,0 +1,43 @@ +/* HP SOM Shared library declarations for GDB, the GNU Debugger. + Copyright (C) 1992 Free Software Foundation, Inc. + +This file is part of GDB. + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +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. + +Written by the Center for Software Science at the Univerity of Utah +and by Cygnus Support. */ + +#ifdef __STDC__ /* Forward decl's for prototypes */ +struct target_ops; +#endif + +/* Called to add symbols from a shared library to gdb's symbol table. */ + +#define SOLIB_ADD(filename, from_tty, targ) \ + som_solib_add (filename, from_tty, targ) + +extern void +som_solib_add PARAMS ((char *, int, struct target_ops *)); + +/* Function to be called when the inferior starts up, to discover the names + of shared libraries that are dynamically linked, the base addresses to + which they are linked, and sufficient information to read in their symbols + at a later time. */ + +#define SOLIB_CREATE_INFERIOR_HOOK(PID) som_solib_create_inferior_hook() + +extern void +som_solib_create_inferior_hook PARAMS((void));