From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 29841 invoked by alias); 18 Feb 2010 09:22:18 -0000 Received: (qmail 29825 invoked by uid 22791); 18 Feb 2010 09:22:16 -0000 X-SWARE-Spam-Status: No, hits=-6.8 required=5.0 tests=AWL,BAYES_00,RCVD_IN_DNSWL_HI,SPF_HELO_PASS,SPF_PASS X-Spam-Check-By: sourceware.org Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Thu, 18 Feb 2010 09:22:08 +0000 Received: from int-mx05.intmail.prod.int.phx2.redhat.com (int-mx05.intmail.prod.int.phx2.redhat.com [10.5.11.18]) by mx1.redhat.com (8.13.8/8.13.8) with ESMTP id o1I9M6nZ029470 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Thu, 18 Feb 2010 04:22:06 -0500 Received: from host0.dyn.jankratochvil.net (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx05.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id o1I9M4p4029474 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO) for ; Thu, 18 Feb 2010 04:22:06 -0500 Received: from host0.dyn.jankratochvil.net (localhost [127.0.0.1]) by host0.dyn.jankratochvil.net (8.14.3/8.14.3) with ESMTP id o1I9M3cG031577 for ; Thu, 18 Feb 2010 10:22:03 +0100 Received: (from jkratoch@localhost) by host0.dyn.jankratochvil.net (8.14.3/8.14.3/Submit) id o1I9M3Vu031576 for gdb-patches@sourceware.org; Thu, 18 Feb 2010 10:22:03 +0100 Date: Thu, 18 Feb 2010 09:22:00 -0000 From: Jan Kratochvil To: gdb-patches@sourceware.org Subject: [patch] Fix crash on stale addrinfo->sectindex Message-ID: <20100218092203.GA31309@host0.dyn.jankratochvil.net> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.5.20 (2009-08-17) X-IsSubscribed: yes 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: 2010-02/txt/msg00452.txt.bz2 Hi, bugreport by Robin Green: https://bugzilla.redhat.com/show_bug.cgi?id=566128 ==1846== Invalid write of size 4 ==1846== at 0x81788CC: relative_addr_info_to_section_offsets (symfile.c:561) ==1846== by 0x808D29B: objfile_relocate (objfiles.c:907) ==1846== by 0x80B823F: svr4_relocate_main_executable (solib-svr4.c:1734) ==1846== by 0x80B82D6: svr4_solib_create_inferior_hook (solib-svr4.c:1810) ==1846== by 0x80A29AA: solib_create_inferior_hook (solib.c:1039) 0x081788cc in relative_addr_info_to_section_offsets (section_offsets=0x9893ac0, num_sections=26, addrs= 0x9892c08) at symfile.c:561 561 section_offsets->offsets[osp->sectindex] = osp->addr; (gdb) p osp->sectindex $1 = 27 (gdb) p *addrs $3 = {num_sections = 29, other = {{addr = 0, name = 0x9892e10 ".interp", sectindex = 0}}} (gdb) up #1 0x0808d29c in objfile_relocate (objfile=0x92b05d0, new_offsets=0xfef1bf60) at objfiles.c:907 907 relative_addr_info_to_section_offsets (new_debug_offsets, (gdb) p debug_objfile->num_sections $2 = 26 (gdb) down #0 0x081788cc in relative_addr_info_to_section_offsets (section_offsets=0x9893ac0, num_sections=26, addrs=0x9892c08) at symfile.c:561 561 section_offsets->offsets[osp->sectindex] = osp->addr; (gdb) p *addrs->other@addrs->num_sections $4 = {{addr = 0, name = 0x9892e10 ".interp", sectindex = 0}, {addr = 0, name = 0x9892e48 ".note.ABI-tag", sectindex = 1}, {addr = 0, name = 0x9892e88 ".note.gnu.build-id", sectindex = 2}, {addr = 0, name = 0x9892ed0 ".gnu.hash", sectindex = 3}, {addr = 0, name = 0x9892f10 ".dynsym", sectindex = 4}, { addr = 0, name = 0x9892f48 ".gnu.liblist", sectindex = 5}, {addr = 0, name = 0x9892f88 ".gnu.version", sectindex = 6}, {addr = 0, name = 0x9892fc8 ".gnu.version_r", sectindex = 7}, {addr = 0, name = 0x9893008 ".rel.dyn", sectindex = 8}, {addr = 0, name = 0x9893048 ".rel.plt", sectindex = 9}, {addr = 0, name = 0x9893088 ".init", sectindex = 10}, { addr = 0, name = 0x98930c0 ".plt", sectindex = 11}, {addr = 0, name = 0x98930f8 ".text", sectindex = 12}, {addr = 0, name = 0x9893130 ".fini", sectindex = 13}, {addr = 0, name = 0x9893168 ".rodata", sectindex = 14}, {addr = 0, name = 0x98931a0 ".eh_frame_hdr", sectindex = 15}, { addr = 0, name = 0x98931e0 ".eh_frame", sectindex = 16}, {addr = 0, name = 0x9893220 ".ctors", sectindex = 17}, {addr = 0, name = 0x9893258 ".dtors", sectindex = 18}, {addr = 0, name = 0x9893290 ".jcr", sectindex = 19}, {addr = 0, name = 0x98932c8 ".dynamic", sectindex = 20}, { addr = 0, name = 0x9893308 ".got", sectindex = 21}, {addr = 0, name = 0x9893340 ".got.plt", sectindex = 22}, {addr = 0, name = 0x9893380 ".data", sectindex = 23}, {addr = 0, name = 0x98933b8 ".bss", sectindex = 24}, {addr = 5440, name = 0x98933f0 ".dynstr", sectindex = 5}, { addr = 0, name = 0x9893428 ".gnu.conflict", sectindex = 26}, {addr = 5440, name = 0x9893468 ".gnu_debuglink", sectindex = 27}, {addr = 5440, name = 0x98934a8 ".gnu.prelink_undo", sectindex = 28}} Initial investigation by Tom Tromey. While it looks as caused by the objfile_relocate() part by me this problem exists in GDB for a long time. Curiously it is not reproducible for me on FSF GDB HEAD but it is reproducible on gdb-7.0.50.20100203-15.fc13. Did not try more. If there is no section with the given name it IMO does not make sense to try setting any parameters for it. No regressions on {x86_64,x86_64-m32,i686}-fedora12-linux-gnu. Thanks, Jan 2010-02-18 Jan Kratochvil * symfile.c (addr_info_make_relative): Extend comment. Move SECT to a more inner block. Initialize ADDR by LOWER_OFFSET only if it was found by bfd_get_section_by_name. * symfile.h (struct section_addr_info) : New comment. --- a/gdb/symfile.c +++ b/gdb/symfile.c @@ -562,13 +562,13 @@ relative_addr_info_to_section_offsets (struct section_offsets *section_offsets, } /* Relativize absolute addresses in ADDRS into offsets based on ABFD. Fill-in - also SECTINDEXes there. */ + also SECTINDEXes specific to ABFD there. This function can be used to + rebase ADDRS to start referencing different BFD than before. */ void addr_info_make_relative (struct section_addr_info *addrs, bfd *abfd) { asection *lower_sect; - asection *sect; CORE_ADDR lower_offset; int i; @@ -597,25 +597,29 @@ addr_info_make_relative (struct section_addr_info *addrs, bfd *abfd) for (i = 0; i < addrs->num_sections && addrs->other[i].name; i++) { - if (addrs->other[i].addr != 0) + asection *sect = bfd_get_section_by_name (abfd, addrs->other[i].name); + + if (sect) { - sect = bfd_get_section_by_name (abfd, addrs->other[i].name); - if (sect) + addrs->other[i].sectindex = sect->index; + + if (addrs->other[i].addr != 0) { addrs->other[i].addr -= bfd_section_vma (abfd, sect); lower_offset = addrs->other[i].addr; /* This is the index used by BFD. */ - addrs->other[i].sectindex = sect->index; } else - { - warning (_("section %s not found in %s"), addrs->other[i].name, - bfd_get_filename (abfd)); - addrs->other[i].addr = 0; - } + addrs->other[i].addr = lower_offset; } else - addrs->other[i].addr = lower_offset; + { + warning (_("section %s not found in %s"), addrs->other[i].name, + bfd_get_filename (abfd)); + addrs->other[i].addr = 0; + + /* SECTINDEX is invalid if ADDR is zero. */ + } } } --- a/gdb/symfile.h +++ b/gdb/symfile.h @@ -80,6 +80,8 @@ struct section_addr_info { CORE_ADDR addr; char *name; + + /* SECTINDEX must be valid for associated BFD if ADDR is not zero. */ int sectindex; } other[1]; };