From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 30950 invoked by alias); 21 Dec 2012 20:21:06 -0000 Received: (qmail 30907 invoked by uid 22791); 21 Dec 2012 20:20:56 -0000 X-SWARE-Spam-Status: No, hits=-1.8 required=5.0 tests=AWL,BAYES_00,RCVD_IN_HOSTKARMA_YE,TW_CP,TW_XZ X-Spam-Check-By: sourceware.org Received: from na3sys009aog109.obsmtp.com (HELO na3sys009aog109.obsmtp.com) (74.125.149.201) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Fri, 21 Dec 2012 20:20:46 +0000 Received: from mx10.qnx.com ([209.226.137.110]) (using TLSv1) by na3sys009aob109.postini.com ([74.125.148.12]) with SMTP ID DSNKUNTEnXegtlL73D8wAbrtPWI5O1luM2/q@postini.com; Fri, 21 Dec 2012 12:20:45 PST Received: by mx10.qnx.com (Postfix, from userid 500) id C9F1520E30; Fri, 21 Dec 2012 15:20:44 -0500 (EST) Received: from exhts.ott.qnx.com (exhts2 [10.222.2.120]) (using TLSv1 with cipher AES128-SHA (128/128 bits)) (No client certificate requested) by mx10.qnx.com (Postfix) with ESMTPS id D4DE320A88 for ; Fri, 21 Dec 2012 15:20:43 -0500 (EST) Received: from [10.222.161.182] (10.222.161.182) by exhts2.ott.qnx.com (10.222.2.25) with Microsoft SMTP Server id 14.2.318.1; Fri, 21 Dec 2012 15:20:43 -0500 Message-ID: <50D4C49A.6040502@qnx.com> Date: Fri, 21 Dec 2012 20:21:00 -0000 From: Aleksandar Ristovski User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/17.0 Thunderbird/17.0 MIME-Version: 1.0 Newsgroups: gmane.comp.gdb.patches To: "gdb-patches@sourceware.org" Subject: [patch] validate binary before use Content-Type: multipart/mixed; boundary="------------030501070005020305000906" Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org X-SW-Source: 2012-12/txt/msg00776.txt.bz2 --------------030501070005020305000906 Content-Type: text/plain; charset="ISO-8859-1"; format=flowed Content-Transfer-Encoding: 7bit Content-length: 2792 Hello all, Currently gdb may use mismatched binary without complaining or noticing. This is particularly often the case when debugging remote targets, or multiple of, with multiple versions of libraries. The situation is possible on self hosted as well. For example, consider having: 1) a library called 'libso.so.1', with SONAME 'libso.so.1'; 2) a program linked against it; 3) environment in which program can be executed and library from 1) found by the dynamic linker; 4) modified libso.so.1, different from the one found by the dynamic linker in 3), in the current working directory of gdb; 5) attach to process stared in 3) using gdb. What happens is, gdb will happily use modified libso.so.1 from current working directory without noticing the mismatch. This causes a lot of confusion. (I can elaborate on the example if needed). Change introduces new target_so_ops function dedicated to performing validation. If we have loaded and relocated the object, validation fails, we throw away bfd and loading of the object fails. The gist of the change is in solib-svr4.c and solib.c The rest are mechanical changes to fill-in new field with valid value. (for bonus points, solib-svr4.c now compiles without -Wno-unused) Regression test suite shows no regressions. (tested on x86_64-unknown-linux-gnu). Thanks, Aleksandar ChangeLog: Aleksandar Ristovski * solib-svr4.c (read_program_headers_from_bfd, read_elf_header_from_bfd): Forward declare. (svr4_keep_data_in_core): Remove unused variable. (read_elf_header_from_target, read_program_headers_from_target, svr4_validate_hdrs_match, svr4_validate): New function. (svr4_read_so_list): Remove unused variable. (read_elf_header_from_bfd): New function. (_initialize_svr4_solib): Use svr4_validate. * solib.c (solib_map_sections): Validate loaded SO. (solib_validate): New function. * solib.h (solib_validate): Declare. * solist.h (target_so_ops): New field 'validate'. * mips-linux-tdep.c (mips_linux_init_abi): Assign validate value. * ppc-linux-tdep.c (ppc_linux_init_abi): Ditto. * solib-darwin.c (_initialize_darwin_solib): Ditto. * solib-dsbt.c (_initialize_dsbt_solib): Ditto. * solib-frv.c (_initialize_frv_solib): Ditto. * solib-ia64-hpux.c (ia64_hpux_target_so_ops): Ditto. * solib-irix.c (_initialize_irix_solib): Ditto. * solib-osf.c (_initialize_osf_solib): Ditto. * solib-pa64.c (_initialize_pa64_solib): Ditto. * solib-som.c (_initialize_som_solib): Ditto. * solib-spu.c (set_spu_solib_ops): Ditto. * solib-sunos.c (_initialize_sunos_solib): Ditto. * solib-target.c (solib.h): Include. (_initialize_solib_target): Assign validate value. --------------030501070005020305000906 Content-Type: text/x-patch; name="solib-validate-201212211440.patch" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="solib-validate-201212211440.patch" Content-length: 19493 Index: gdb/solib-svr4.c =================================================================== RCS file: /cvs/src/src/gdb/solib-svr4.c,v retrieving revision 1.171 diff -u -p -r1.171 solib-svr4.c --- gdb/solib-svr4.c 13 Dec 2012 21:29:50 -0000 1.171 +++ gdb/solib-svr4.c 21 Dec 2012 19:40:44 -0000 @@ -51,6 +51,8 @@ static struct link_map_offsets *svr4_fetch_link_map_offsets (void); static int svr4_have_link_map_offsets (void); static void svr4_relocate_main_executable (void); +static gdb_byte *read_program_headers_from_bfd (bfd *abfd, int *phdrs_size); +static gdb_byte *read_elf_header_from_bfd (bfd *abfd, int *bfd_ehdr_size); /* Link map info to include in an allocated so_list entry. */ @@ -849,7 +851,6 @@ svr4_keep_data_in_core (CORE_ADDR vaddr, CORE_ADDR ldsomap; struct so_list *new; struct cleanup *old_chain; - struct link_map_offsets *lmo; CORE_ADDR name_lm; info = get_svr4_info (); @@ -863,7 +864,6 @@ svr4_keep_data_in_core (CORE_ADDR vaddr, if (!ldsomap) return 0; - lmo = svr4_fetch_link_map_offsets (); new = XZALLOC (struct so_list); old_chain = make_cleanup (xfree, new); new->lm_info = lm_info_read (ldsomap); @@ -874,6 +874,201 @@ svr4_keep_data_in_core (CORE_ADDR vaddr, return (name_lm >= vaddr && name_lm < vaddr + size); } + +/* Read elf header corresponding to SO from target memory. + Allocates memory for the returned value (which ought be + freed with xfree). Returns elf header size in *HDR_SIZE. */ + +static gdb_byte * +read_elf_header_from_target (const struct so_list *const so, + int *const hdr_size) +{ + const CORE_ADDR so_base_addr = so->lm_info->l_addr; + const int ptr_size + = builtin_type (target_gdbarch ())->builtin_data_ptr->length; + const gdb_byte elf_magic[] = { 0x7f, 'E', 'L', 'F' }; + int status; + gdb_byte *ret; + + if (!so->lm_info->l_addr_p) + { + warning (_("Unable to load elf header from target since shared object %s has not been relocated."), so->abfd->filename); + return NULL; + } + + *hdr_size = (ptr_size == 4)? sizeof (Elf32_External_Ehdr) + : sizeof (Elf64_External_Ehdr); + + ret = xzalloc (*hdr_size); + + if (ret == NULL) + { + warning (_("Unable to load elf header from target due to out of memory.")); + return NULL; + } + + if ((status = target_read_memory (so_base_addr, ret, *hdr_size)) != 0) + { + warning (_("Unable to load elf header from target due to failed memory read at address %s"), + paddress (target_gdbarch (), so_base_addr)); + xfree (ret); + return NULL; + } + + /* Verify that we have actually read the header. */ + if (memcmp (elf_magic, ret, 4) != 0) + { + warning (_("Unable to load elf header from target due to elf magic string mismatch.")); + xfree (ret); + return NULL; + } + + return ret; +} + + +/* Read program headers from target memory for a given shared object. + SO must have been relocated and its addr_low correctly set. */ + +static gdb_byte * +read_program_headers_from_target (const struct so_list *const so, + int *const phdrs_size) +{ + const CORE_ADDR so_base_addr = so->lm_info->l_addr; + const enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch ()); + const int ptr_size + = builtin_type (target_gdbarch ())->builtin_data_ptr->length; + union ElfXX_Ehdr + { + Elf32_External_Ehdr _32; + Elf64_External_Ehdr _64; + } ELF_EHDR; + unsigned phnum, phentsize, phoff; /* In our byte order */ + int ehdr_size; + int status; + gdb_byte *e_phnum, *e_phentsize, *e_phoff; + int e_phnum_len, e_phentsize_len, e_phoff_len; + gdb_byte *ret; + + if (!so->lm_info->l_addr_p) + { + warning (_("Unable to load program headers from target since shared object %s has not been relocated."), so->abfd->filename); + return NULL; + } + + ret = read_elf_header_from_target (so, &ehdr_size); + + if (ret == NULL) + return NULL; + + memcpy (&ELF_EHDR, ret, ehdr_size); + xfree (ret); + + if (ptr_size == 4) + { + e_phnum = (gdb_byte *) &ELF_EHDR._32.e_phnum; + e_phnum_len = sizeof (ELF_EHDR._32.e_phnum); + e_phentsize = (gdb_byte *) &ELF_EHDR._32.e_phentsize; + e_phentsize_len = sizeof (ELF_EHDR._32.e_phentsize); + e_phoff = (gdb_byte *) &ELF_EHDR._32.e_phoff; + e_phoff_len = sizeof (ELF_EHDR._32.e_phoff); + } + else + { + e_phnum = (gdb_byte *) &ELF_EHDR._64.e_phnum; + e_phnum_len = sizeof (ELF_EHDR._64.e_phnum); + e_phentsize = (gdb_byte *) &ELF_EHDR._64.e_phentsize; + e_phentsize_len = sizeof (ELF_EHDR._64.e_phentsize); + e_phoff = (gdb_byte *) &ELF_EHDR._64.e_phoff; + e_phoff_len = sizeof (ELF_EHDR._64.e_phoff); + } + + phnum = extract_unsigned_integer (e_phnum, e_phnum_len, byte_order); + phentsize = extract_unsigned_integer (e_phentsize, e_phentsize_len, + byte_order); + phoff = extract_unsigned_integer (e_phoff, e_phoff_len, byte_order); + + *phdrs_size = phnum * phentsize; + + ret = xzalloc (*phdrs_size); + if (ret == NULL) + { + warning (_("Unable to load target pheaders due to out of memory.")); + return NULL; + } + + if ((status = target_read_memory (so_base_addr + phoff, ret, *phdrs_size)) + != 0) + { + memory_error (status, so_base_addr + phoff); + xfree (ret); + return NULL; + } + + return ret; +} + +/* Validate elf header and phdrs of SO->ABFD and in-memory match. */ + +static int +svr4_validate_hdrs_match (const struct so_list *const so) +{ + int mem_ehdr_size, bfd_ehdr_size; + int mem_phdrs_size, bfd_phdrs_size; + gdb_byte *mem_ehdr, *mem_phdrs = NULL; + gdb_byte *bfd_ehdr = NULL, *bfd_phdrs = NULL; + int ok = 1; + + mem_ehdr = read_elf_header_from_target (so, &mem_ehdr_size); + if (mem_ehdr) + mem_phdrs = read_program_headers_from_target (so, &mem_phdrs_size); + if (mem_phdrs) + bfd_ehdr = read_elf_header_from_bfd (so->abfd, &bfd_ehdr_size); + if (bfd_ehdr) + bfd_phdrs = read_program_headers_from_bfd (so->abfd, &bfd_phdrs_size); + + if (bfd_phdrs != NULL) + { + /* Finally, check. Since both memory and file representations + must match, it is o.k. to bit compare headers. */ + if (bfd_ehdr_size != mem_ehdr_size + || memcmp (mem_ehdr, bfd_ehdr, mem_ehdr_size) != 0) + { + warning (_("Elf header does not match for %s"), + so->abfd->filename); + ok = 0; + } + else if (bfd_phdrs_size != mem_phdrs_size + || memcmp (mem_phdrs, bfd_phdrs, mem_phdrs_size) != 0) + { + warning (_("Program headers do not match for %s"), + so->abfd->filename); + ok = 0; + } + } + else + warning (_("Unable to validate binary match for %s"), so->abfd->filename); + + xfree (bfd_phdrs); + xfree (bfd_ehdr); + xfree (mem_phdrs); + xfree (mem_ehdr); + + return ok; +} + +/* Validate SO by checking whether opened file matches + in-memory object. */ + +static int +svr4_validate(const struct so_list *const so) +{ + gdb_assert (so != NULL); + gdb_assert (so->abfd != NULL); + + return svr4_validate_hdrs_match (so); +} + /* Implement the "open_symbol_file_object" target_so_ops method. If no open symbol file, attempt to locate and open the main symbol @@ -1176,7 +1371,6 @@ svr4_read_so_list (CORE_ADDR lm, struct for (; lm != 0; prev_lm = lm, lm = next_lm) { - struct link_map_offsets *lmo = svr4_fetch_link_map_offsets (); struct so_list *new; struct cleanup *old_chain; int errcode; @@ -1741,6 +1935,36 @@ svr4_special_symbol_handling (void) /* Nothing to do. */ } +/* Read the ELF header from ABFD. Return the raw contents and + set *ELFHDR_SIZE to the size of the elf header. */ + +static gdb_byte * +read_elf_header_from_bfd (bfd *const abfd, int *const bfd_ehdr_size) +{ + const int ptr_size + = builtin_type (target_gdbarch ())->builtin_data_ptr->length; + const int ehdr_size = (ptr_size == 4)? sizeof (Elf32_External_Ehdr) + : sizeof (Elf64_External_Ehdr); + gdb_byte *const bfd_ehdr = xmalloc (ehdr_size); + + if (bfd_ehdr == NULL) + { + warning (_("Unable to read raw elf header due to out of memory.")); + return NULL; + } + + *bfd_ehdr_size = ehdr_size; + + if (bfd_seek (abfd, 0, SEEK_SET) != 0 + || bfd_bread (bfd_ehdr, ehdr_size, abfd) != ehdr_size) + { + warning (_("Unable to read raw elf header due to failed file operation.")); + xfree (bfd_ehdr); + return NULL; + } + return bfd_ehdr; +} + /* Read the ELF program headers from ABFD. Return the contents and set *PHDRS_SIZE to the size of the program headers. */ @@ -2462,4 +2686,5 @@ _initialize_svr4_solib (void) svr4_so_ops.lookup_lib_global_symbol = elf_lookup_lib_symbol; svr4_so_ops.same = svr4_same; svr4_so_ops.keep_data_in_core = svr4_keep_data_in_core; + svr4_so_ops.validate = svr4_validate; } Index: gdb/solib.c =================================================================== RCS file: /cvs/src/src/gdb/solib.c,v retrieving revision 1.168 diff -u -p -r1.168 solib.c --- gdb/solib.c 9 Nov 2012 19:58:01 -0000 1.168 +++ gdb/solib.c 21 Dec 2012 19:40:47 -0000 @@ -495,6 +495,15 @@ solib_map_sections (struct so_list *so) } } + if (!ops->validate (so)) + { + warning (_("Shared object could not be validated and will be ignored: %s."), + so->abfd->filename); + gdb_bfd_unref (so->abfd); + so->abfd = NULL; + return 0; + } + /* Add the shared object's sections to the current set of file section tables. Do this immediately after mapping the object so that later nodes in the list can query this object, as is needed @@ -1448,6 +1457,14 @@ gdb_bfd_lookup_symbol (bfd *abfd, return symaddr; } +/* Default implementation does not perform any validation. */ + +int +solib_validate (const struct so_list *const so) +{ + return 1; /* No validation. */ +} + extern initialize_file_ftype _initialize_solib; /* -Wmissing-prototypes */ void Index: gdb/solib.h =================================================================== RCS file: /cvs/src/src/gdb/solib.h,v retrieving revision 1.33 diff -u -p -r1.33 solib.h --- gdb/solib.h 3 Feb 2012 15:19:37 -0000 1.33 +++ gdb/solib.h 21 Dec 2012 19:40:49 -0000 @@ -91,4 +91,8 @@ extern CORE_ADDR gdb_bfd_lookup_symbol_f void *), void *data); +/* Default validation always returns 1. */ + +extern int solib_validate (const struct so_list *so); + #endif /* SOLIB_H */ Index: gdb/solist.h =================================================================== RCS file: /cvs/src/src/gdb/solist.h,v retrieving revision 1.37 diff -u -p -r1.37 solist.h --- gdb/solist.h 4 Jan 2012 08:17:11 -0000 1.37 +++ gdb/solist.h 21 Dec 2012 19:40:51 -0000 @@ -149,6 +149,11 @@ struct target_so_ops core file (in particular, for readonly sections). */ int (*keep_data_in_core) (CORE_ADDR vaddr, unsigned long size); + + + /* Return 0 if SO does not match target SO it is supposed to + represent. Return 1 otherwise. */ + int (*validate) (const struct so_list *so); }; /* Free the memory associated with a (so_list *). */ Index: gdb/mips-linux-tdep.c =================================================================== RCS file: /cvs/src/src/gdb/mips-linux-tdep.c,v retrieving revision 1.96 diff -u -p -r1.96 mips-linux-tdep.c --- gdb/mips-linux-tdep.c 9 Nov 2012 19:57:59 -0000 1.96 +++ gdb/mips-linux-tdep.c 21 Dec 2012 19:40:53 -0000 @@ -1495,6 +1495,8 @@ mips_linux_init_abi (struct gdbarch_info mips_svr4_so_ops.in_dynsym_resolve_code = mips_linux_in_dynsym_resolve_code; } + if (mips_svr4_so_ops.validate == NULL) + mips_svr4_so_ops.validate = solib_validate; set_solib_ops (gdbarch, &mips_svr4_so_ops); set_gdbarch_write_pc (gdbarch, mips_linux_write_pc); Index: gdb/ppc-linux-tdep.c =================================================================== RCS file: /cvs/src/src/gdb/ppc-linux-tdep.c,v retrieving revision 1.140 diff -u -p -r1.140 ppc-linux-tdep.c --- gdb/ppc-linux-tdep.c 8 Nov 2012 14:16:33 -0000 1.140 +++ gdb/ppc-linux-tdep.c 21 Dec 2012 19:40:55 -0000 @@ -1733,6 +1733,8 @@ ppc_linux_init_abi (struct gdbarch_info powerpc_so_ops.in_dynsym_resolve_code = powerpc_linux_in_dynsym_resolve_code; } + if (powerpc_so_ops.validate == NULL) + powerpc_so_ops.validate = solib_validate; set_solib_ops (gdbarch, &powerpc_so_ops); set_gdbarch_skip_solib_resolver (gdbarch, glibc_skip_solib_resolver); Index: gdb/solib-darwin.c =================================================================== RCS file: /cvs/src/src/gdb/solib-darwin.c,v retrieving revision 1.34 diff -u -p -r1.34 solib-darwin.c --- gdb/solib-darwin.c 18 Dec 2012 06:19:54 -0000 1.34 +++ gdb/solib-darwin.c 21 Dec 2012 19:40:58 -0000 @@ -647,4 +647,5 @@ _initialize_darwin_solib (void) darwin_so_ops.in_dynsym_resolve_code = darwin_in_dynsym_resolve_code; darwin_so_ops.lookup_lib_global_symbol = darwin_lookup_lib_symbol; darwin_so_ops.bfd_open = darwin_bfd_open; + darwin_so_ops.validate = solib_validate; } Index: gdb/solib-dsbt.c =================================================================== RCS file: /cvs/src/src/gdb/solib-dsbt.c,v retrieving revision 1.8 diff -u -p -r1.8 solib-dsbt.c --- gdb/solib-dsbt.c 9 Nov 2012 19:58:00 -0000 1.8 +++ gdb/solib-dsbt.c 21 Dec 2012 19:41:00 -0000 @@ -1182,6 +1182,7 @@ _initialize_dsbt_solib (void) dsbt_so_ops.open_symbol_file_object = open_symbol_file_object; dsbt_so_ops.in_dynsym_resolve_code = dsbt_in_dynsym_resolve_code; dsbt_so_ops.bfd_open = solib_bfd_open; + dsbt_so_ops.validate = solib_validate; /* Debug this file's internals. */ add_setshow_zuinteger_cmd ("solib-dsbt", class_maintenance, Index: gdb/solib-frv.c =================================================================== RCS file: /cvs/src/src/gdb/solib-frv.c,v retrieving revision 1.48 diff -u -p -r1.48 solib-frv.c --- gdb/solib-frv.c 9 Nov 2012 19:58:00 -0000 1.48 +++ gdb/solib-frv.c 21 Dec 2012 19:41:02 -0000 @@ -1182,6 +1182,7 @@ _initialize_frv_solib (void) frv_so_ops.open_symbol_file_object = open_symbol_file_object; frv_so_ops.in_dynsym_resolve_code = frv_in_dynsym_resolve_code; frv_so_ops.bfd_open = solib_bfd_open; + frv_so_ops.validate = solib_validate; /* Debug this file's internals. */ add_setshow_zuinteger_cmd ("solib-frv", class_maintenance, Index: gdb/solib-ia64-hpux.c =================================================================== RCS file: /cvs/src/src/gdb/solib-ia64-hpux.c,v retrieving revision 1.5 diff -u -p -r1.5 solib-ia64-hpux.c --- gdb/solib-ia64-hpux.c 9 Nov 2012 19:58:00 -0000 1.5 +++ gdb/solib-ia64-hpux.c 21 Dec 2012 19:41:04 -0000 @@ -686,6 +686,7 @@ ia64_hpux_target_so_ops (void) ops->open_symbol_file_object = ia64_hpux_open_symbol_file_object; ops->in_dynsym_resolve_code = ia64_hpux_in_dynsym_resolve_code; ops->bfd_open = solib_bfd_open; + ops->validate = solib_validate; return ops; } Index: gdb/solib-irix.c =================================================================== RCS file: /cvs/src/src/gdb/solib-irix.c,v retrieving revision 1.45 diff -u -p -r1.45 solib-irix.c --- gdb/solib-irix.c 9 Nov 2012 19:58:00 -0000 1.45 +++ gdb/solib-irix.c 21 Dec 2012 19:41:06 -0000 @@ -653,4 +653,5 @@ _initialize_irix_solib (void) irix_so_ops.open_symbol_file_object = irix_open_symbol_file_object; irix_so_ops.in_dynsym_resolve_code = irix_in_dynsym_resolve_code; irix_so_ops.bfd_open = solib_bfd_open; + irix_so_ops.validate = solib_validate; } Index: gdb/solib-osf.c =================================================================== RCS file: /cvs/src/src/gdb/solib-osf.c,v retrieving revision 1.37 diff -u -p -r1.37 solib-osf.c --- gdb/solib-osf.c 24 May 2012 16:51:36 -0000 1.37 +++ gdb/solib-osf.c 21 Dec 2012 19:41:09 -0000 @@ -634,6 +634,7 @@ _initialize_osf_solib (void) osf_so_ops.open_symbol_file_object = osf_open_symbol_file_object; osf_so_ops.in_dynsym_resolve_code = osf_in_dynsym_resolve_code; osf_so_ops.bfd_open = solib_bfd_open; + osf_so_ops.validate = solib_validate; /* FIXME: Don't do this here. *_gdbarch_init() should set so_ops. */ current_target_so_ops = &osf_so_ops; Index: gdb/solib-pa64.c =================================================================== RCS file: /cvs/src/src/gdb/solib-pa64.c,v retrieving revision 1.39 diff -u -p -r1.39 solib-pa64.c --- gdb/solib-pa64.c 9 Nov 2012 19:58:01 -0000 1.39 +++ gdb/solib-pa64.c 21 Dec 2012 19:41:11 -0000 @@ -623,6 +623,7 @@ _initialize_pa64_solib (void) pa64_so_ops.open_symbol_file_object = pa64_open_symbol_file_object; pa64_so_ops.in_dynsym_resolve_code = pa64_in_dynsym_resolve_code; pa64_so_ops.bfd_open = solib_bfd_open; + pa64_so_ops.validate = solib_validate; memset (&dld_cache, 0, sizeof (dld_cache)); } Index: gdb/solib-som.c =================================================================== RCS file: /cvs/src/src/gdb/solib-som.c,v retrieving revision 1.38 diff -u -p -r1.38 solib-som.c --- gdb/solib-som.c 9 Nov 2012 19:58:01 -0000 1.38 +++ gdb/solib-som.c 21 Dec 2012 19:41:13 -0000 @@ -811,6 +811,7 @@ _initialize_som_solib (void) som_so_ops.open_symbol_file_object = som_open_symbol_file_object; som_so_ops.in_dynsym_resolve_code = som_in_dynsym_resolve_code; som_so_ops.bfd_open = solib_bfd_open; + som_so_ops.validate = solib_validate; } void Index: gdb/solib-spu.c =================================================================== RCS file: /cvs/src/src/gdb/solib-spu.c,v retrieving revision 1.23 diff -u -p -r1.23 solib-spu.c --- gdb/solib-spu.c 9 Nov 2012 19:58:01 -0000 1.23 +++ gdb/solib-spu.c 21 Dec 2012 19:41:15 -0000 @@ -519,6 +519,7 @@ set_spu_solib_ops (struct gdbarch *gdbar spu_so_ops.current_sos = spu_current_sos; spu_so_ops.bfd_open = spu_bfd_open; spu_so_ops.lookup_lib_global_symbol = spu_lookup_lib_symbol; + spu_so_ops.validate = solib_validate; } set_solib_ops (gdbarch, &spu_so_ops); Index: gdb/solib-sunos.c =================================================================== RCS file: /cvs/src/src/gdb/solib-sunos.c,v retrieving revision 1.50 diff -u -p -r1.50 solib-sunos.c --- gdb/solib-sunos.c 9 Nov 2012 19:58:01 -0000 1.50 +++ gdb/solib-sunos.c 21 Dec 2012 19:41:17 -0000 @@ -739,6 +739,7 @@ _initialize_sunos_solib (void) sunos_so_ops.open_symbol_file_object = open_symbol_file_object; sunos_so_ops.in_dynsym_resolve_code = sunos_in_dynsym_resolve_code; sunos_so_ops.bfd_open = solib_bfd_open; + sunos_so_ops.validate = solib_validate; /* FIXME: Don't do this here. *_gdbarch_init() should set so_ops. */ current_target_so_ops = &sunos_so_ops; Index: gdb/solib-target.c =================================================================== RCS file: /cvs/src/src/gdb/solib-target.c,v retrieving revision 1.25 diff -u -p -r1.25 solib-target.c --- gdb/solib-target.c 14 Dec 2012 23:27:13 -0000 1.25 +++ gdb/solib-target.c 21 Dec 2012 19:41:19 -0000 @@ -25,6 +25,7 @@ #include "target.h" #include "vec.h" #include "solib-target.h" +#include "solib.h" #include "gdb_string.h" @@ -501,6 +502,7 @@ _initialize_solib_target (void) solib_target_so_ops.in_dynsym_resolve_code = solib_target_in_dynsym_resolve_code; solib_target_so_ops.bfd_open = solib_bfd_open; + solib_target_so_ops.validate = solib_validate; /* Set current_target_so_ops to solib_target_so_ops if not already set. */ --------------030501070005020305000906--