From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 50467 invoked by alias); 7 Aug 2015 02:03:24 -0000 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 Received: (qmail 50456 invoked by uid 89); 7 Aug 2015 02:03:24 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=0.4 required=5.0 tests=AWL,BAYES_05,KAM_LAZY_DOMAIN_SECURITY,LIKELY_SPAM_BODY,RP_MATCHES_RCVD,SPF_HELO_PASS autolearn=no version=3.3.2 X-HELO: mx1.redhat.com Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES256-GCM-SHA384 encrypted) ESMTPS; Fri, 07 Aug 2015 02:03:21 +0000 Received: from int-mx14.intmail.prod.int.phx2.redhat.com (int-mx14.intmail.prod.int.phx2.redhat.com [10.5.11.27]) by mx1.redhat.com (Postfix) with ESMTPS id C292F32B58F; Fri, 7 Aug 2015 02:03:19 +0000 (UTC) Received: from localhost (unused-10-15-17-51.yyz.redhat.com [10.15.17.51]) by int-mx14.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id t76MHrdr028814 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=NO); Thu, 6 Aug 2015 18:17:54 -0400 From: Sergio Durigan Junior To: Joel Brobecker Cc: "Jose E. Marchesi" , gdb-patches@sourceware.org Subject: Re: [PATCH V4 5/9] New probe type: DTrace USDT probes. References: <1422874968-382-1-git-send-email-jose.marchesi@oracle.com> <1422874968-382-6-git-send-email-jose.marchesi@oracle.com> <87r3tp722i.fsf@redhat.com> <20150325191418.GA32233@adacore.com> <87bnjfraq1.fsf@oracle.com> <20150326175028.GA13867@adacore.com> <87y4mdjcie.fsf@oracle.com> <20150331184727.GF13867@adacore.com> <878uedey48.fsf@oracle.com> <20150806213103.GC14992@adacore.com> X-URL: http://blog.sergiodj.net Date: Fri, 07 Aug 2015 02:03:00 -0000 In-Reply-To: <20150806213103.GC14992@adacore.com> (Joel Brobecker's message of "Thu, 6 Aug 2015 14:31:03 -0700") Message-ID: <87r3ngf4dq.fsf@redhat.com> User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.5 (gnu/linux) MIME-Version: 1.0 Content-Type: text/plain X-IsSubscribed: yes X-SW-Source: 2015-08/txt/msg00188.txt.bz2 On Thursday, August 06 2015, Joel Brobecker wrote: > I finally had a bit of time to look into this again. I concluded > that the DOF data is invalid, or follows a format that's different > from the one that GDB expected, and so added some code to detect > and ignore... Attached is the patch with full explanation. Does it > make sense to you? > > gdb/ChangeLog: > > * dtrace-probe.c (dtrace_process_dof): Ignore the objfile's DOF > data if a DTRACE_DOF_SECT_TYPE_PROVIDER section is found to be > smaller than expected. > > Tested on x86_64-linux (official GDB testsuite) + x86-solaris > (AdaCore's testsuite). Pretty nice investigation, Joel! This patch makes sense to me and is OK to go in (it just has a small typo below). Something I don't like about this goto scheme is that it doesn't contain useful information as to why the section has been discarded ("... does not contain valid DOF data" is too generic). But I'm just speaking my mind here; this has nothing to do with your patch :-). > Thanks, > -- > Joel > > From 84179e3ce4008f36cbdbb4edf040d94b5f03b4c2 Mon Sep 17 00:00:00 2001 > From: Joel Brobecker > Date: Thu, 6 Aug 2015 22:13:32 +0200 > Subject: [PATCH] [DTRACE] ignore invalid DOF provider sections > > On x86-solaris 10, we noticed that starting a program would sometimes > cause the debugger to crash. For instance: > > % gdb a > (gdb) break adainit > Breakpoint 1 at 0x8051f03 > (gdb) run > Starting program: /[...]/a > [Thread debugging using libthread_db enabled] > zsh: 24398 segmentation fault (core dumped) /[...]/gdb a > > The exception occurs in dtrace_process_dof_probe, while trying > to process each probe referenced by a DTRACE_DOF_SECT_TYPE_PROVIDER > DOF section from /lib/libc.so.1. For reference, the ELF section > in that shared library providing the DOF data has the following > characteristics: > > Idx Name Size VMA LMA File off Algn > 14 .SUNW_dof 0000109d 000b4398 000b4398 000b4398 2**3 > CONTENTS, ALLOC, LOAD, READONLY, DATA > > The function dtrace_process_dof gets passed the contents of that > ELF section, which allows is to determine the location of the table ^^ "it" ? > where all DOF sections are described. I dumped the contents of > each DOF section as seen by GDB, and it seemed to be plausible, > because the offset of each DOF section was pretty much equal to > the sum of the offset and size of the previous DOF section. Also, > the offset + sum of the last section corresponds to the size of > the .SUNW_dof section. > > Things start to break down when processing one of the DOF sections > that has a type of DTRACE_DOF_SECT_TYPE_PROVIDER. It gets the contents > of this DOF section via: > > struct dtrace_dof_provider *provider = (struct dtrace_dof_provider *) > DTRACE_DOF_PTR (dof, DOF_UINT (dof, section->dofs_offset)); > > Said more simply, the struct dtrace_dof_provider data is at > section->dofs_offset of the entire DOF contents. Given that > the contents of SECTION seemed to make sense, so far so good. > > However, what SECTION tells us is that our DOF provider section > is 40 bytes long: > > (gdb) print *section > $36 = {dofs_type = 15, dofs_align = 4, dofs_flags = 1, > dofs_entsize = 0, dofs_offset = 3264, dofs_size = 40} > ^^^^^^^^^^^^^^ > > But on the other hand: > > (gdb) p sizeof (struct dtrace_dof_provider) > $54 = 44 > > In other words GDB expected a bigger DOF section and when we try to > fetch the value of the last field of that DOF section (dofpv_prenoffs)... > > eoffsets_s = DTRACE_DOF_SECT (dof, > DOF_UINT (dof, provider->dofpv_prenoffs)); > > ... we end up reading data that actually belongs to another DOF > section, and therefore irrelevant. This in turn means that the value > of eofftab gets incorrectly set, since it depends on eoffsets_s: > > eofftab = DTRACE_DOF_PTR (dof, DOF_UINT (dof, eoffsets_s->dofs_offset)); > > This invalid address quickly catches up to us when we pass it to > dtrace_process_dof_probe shortly after, where we crash because > we try to subscript it: > > Program received signal SIGSEGV, Segmentation fault. > 0x08155bba in dtrace_process_dof_probe ([...]) at [...]/dtrace-probe.c:378 > 378 = ((uint32_t *) eofftab)[...]; > > This patch fixes the issue by detecting provider DOF sections > that are smaller than expected, and discarding the DOF data. > > gdb/ChangeLog: > > * dtrace-probe.c (dtrace_process_dof): Ignore the objfile's DOF > data if a DTRACE_DOF_SECT_TYPE_PROVIDER section is found to be > smaller than expected. > --- > gdb/dtrace-probe.c | 8 ++++++++ > 1 file changed, 8 insertions(+) > > diff --git a/gdb/dtrace-probe.c b/gdb/dtrace-probe.c > index 3f2548d..9816f07 100644 > --- a/gdb/dtrace-probe.c > +++ b/gdb/dtrace-probe.c > @@ -519,6 +519,14 @@ dtrace_process_dof (asection *sect, struct objfile *objfile, > unsigned int entsize = DOF_UINT (dof, probes_s->dofs_entsize); > int num_probes; > > + if (DOF_UINT (dof, section->dofs_size) > + < sizeof (struct dtrace_dof_provider)) > + { > + /* The section is smaller than expected, so do not use it. > + This has been observed on x86-solaris 10. */ > + goto invalid_dof_data; > + } > + > /* Very, unlikely, but could crash gdb if not handled > properly. */ > if (entsize == 0) > -- > 1.7.10.4 > Thanks, -- Sergio GPG key ID: 237A 54B1 0287 28BF 00EF 31F4 D0EB 7628 65FC 5E36 Please send encrypted e-mail if possible http://sergiodj.net/