bug-bash
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Running bash under valgrind gives "invalid free()"


From: Chet Ramey
Subject: Re: Running bash under valgrind gives "invalid free()"
Date: Wed, 12 Apr 2017 10:49:33 -0400
User-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.12; rv:45.0) Gecko/20100101 Thunderbird/45.8.0

On 4/12/17 9:59 AM, Reuben Thomas wrote:
> ​O​
> n 12 April 2017 at 14:50, Chet Ramey <chet.ramey@case.edu
> <mailto:chet.ramey@case.edu>> wrote:
> 
>     On 4/12/17 8:57 AM, Reuben Thomas wrote:
>     > See https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=849517
>     <https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=849517>
>     >
>     > ​I can reproduce this also in bash 4.3 as supplied with Ubuntu 16.04, 
> and
>     > in a build of 4.4 from source on my Ubuntu system.
>     >
>     > ​As stated in the bug report, the bug causes problems beyond bash, as it
>     > causes build systems to think that valgrind is not working, and hence 
> run
>     > tests without it.
> 
>     Look at it this way: if the "bug" can't be reproduced on another OS, or
>     can't be reproduced using a debugging malloc library other than valgrind,
>     that points the finger at valgrind or Debian.
> 
> 
> ​Apologies, I didn't think of reproducibility on other OSes. (Though the
> point about valgrind is not a strong one: ​

It's a false positive, or a bug in valgrind. I took a quick look.  There's
one place in this code path where free() gets called.  Here's the trace:

1. the -c option causes run_one_command() to call parse_and_execute() with
   a dynamically-allocated string. Let's say its address is 0x7bd218

2. parse_and_execute calls parse_prologue with that string as the "string"
   argument. The value of "string" is still 0x7bd218.

3. parse_prologue assigns the value of string to "orig_string". orig_string
   still has the value 0x7bd218.

4. parse_prologue calls add_unwind_protect to arrange for that memory to be
   freed.  The unwind-protect structure that gets created has (simplified)
        uwp->cleanup = xfree
        uwp->argument = orig_string (still with the value 0x7bd218)

5. parse_and_execute runs the command, and calls run_unwind_frame. That
   calls each cleanup function in turn. xfree() gets called with a pointer
   whose value is 0x7bd218, frees it, and returns.

Before you ask, the string in step 1 is allocated by savestring(), which is
defined as

define savestring(x) (char *)strcpy (xmalloc (1 + strlen (x)), (x))

There's no place where that value is part of a data segment.

Chet
-- 
``The lyf so short, the craft so long to lerne.'' - Chaucer
                 ``Ars longa, vita brevis'' - Hippocrates
Chet Ramey, UTech, CWRU    chet@case.edu    http://cnswww.cns.cwru.edu/~chet/



reply via email to

[Prev in Thread] Current Thread [Next in Thread]