Bug 173283 - memory leak in bash
Summary: memory leak in bash
Keywords:
Status: CLOSED RAWHIDE
Alias: None
Product: Fedora
Classification: Fedora
Component: bash
Version: rawhide
Hardware: All
OS: Linux
medium
high
Target Milestone: ---
Assignee: Tim Waugh
QA Contact: Ben Levenson
URL:
Whiteboard:
Depends On:
Blocks: FC6Target
TreeView+ depends on / blocked
 
Reported: 2005-11-15 22:06 UTC by Steve Grubb
Modified: 2009-11-12 09:11 UTC (History)
3 users (show)

Fixed In Version:
Doc Type: Bug Fix
Doc Text:
Clone Of:
: 537029 (view as bug list)
Environment:
Last Closed: 2006-07-13 17:35:13 UTC
Type: ---
Embargoed:


Attachments (Terms of Use)
Patch fixing memory leaks (986 bytes, patch)
2005-11-15 22:07 UTC, Steve Grubb
no flags Details | Diff
nonblock.c (1.89 KB, text/plain)
2005-12-07 17:46 UTC, Tim Waugh
no flags Details
bash-read-memleak.patch (355 bytes, patch)
2005-12-07 18:02 UTC, Tim Waugh
no flags Details | Diff

Description Steve Grubb 2005-11-15 22:06:46 UTC
From Bugzilla Helper:
User-Agent: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.7.12) Gecko/20050922 Fedora/1.0.7-1.1.fc4 Firefox/1.0.7

Description of problem:
There is a memory leak in bash. It can be triggered by putting read command in a loop where the read fails due to no input (pipe for stdin).

Version-Release number of selected component (if applicable):
bash-3.0-36

How reproducible:
Always

Steps to Reproduce:
1. Described above

Actual Results:  OOM killer zaps random processes and top shows memory consumption grow.

Expected Results:  top steady & no OOM killer.

Additional info:

I will attach a patch addressing this.

Comment 1 Steve Grubb 2005-11-15 22:07:57 UTC
Created attachment 121097 [details]
Patch fixing memory leaks

Please apply to rawhide.

Comment 2 Tim Waugh 2005-12-06 10:15:25 UTC
Steve, this is how you said to reproduce the problem:

-->
If you wanted to see the bug, install the latest rawhide audit package.
In /etc/auditd.conf, add this line:

dispatcher = /home/homedir/autest

Then save this script to that location:

#!/bin/sh

msg_type="SELINUX"
while [ 1 ]
do {
        read -t 5 line 2>/dev/null
        if [ ! -z "$line" ] ; then
                tmp=`echo $line | grep $msg_type`
                if [ x"$tmp" != "x" ] ; then
                        echo "Test script AVC: $tmp"
                fi
        fi
}
done

Restart the audit daemon. Using top, you should see the memory usage climbing
quickly.
<--

This is quite a long-winded method!  Is there a simpler way to trigger it,
perhaps by just running that script on some large input file you can provide?

Ideally I'd like an RHTS test case for this bug, so we can see what other
releases are affected and make sure we don't regress on it in the future.

Comment 3 Steve Grubb 2005-12-06 11:30:13 UTC
A file being piped in won't trigger it since the file is likely to be readable.
The bug/leak is triggered when the input source is not ready to send data and
the reader (bash) determines it to be an error. I'll see if there's another way
to trigger it.

My guess is that some prior versions of bash 3 are affected by this.

Comment 4 Tim Waugh 2005-12-07 14:32:08 UTC
This patch doesn't look necessary to me, and here's why:

  /* This *must* be the top unwind-protect on the stack, so the manipulation
     of the unwind-protect stack after the realloc() works right. */
  add_unwind_protect (xfree, input_string);

This line is meant to deal with freeing up the allocating string I think.

I tried tickling two of the three bugs:

declare -r foo
echo a | read foo

sleep 2 | read -t 1

under valgrind, and could not see any resulting memory leaks.  I couldn't quite
work out how to tickle the third case.

Comment 5 Tim Waugh 2005-12-07 14:36:41 UTC
Of course, your original method does indeed show that there is a leak.  I'd just
like to be able to pin it down a bit more.

Comment 6 Steve Grubb 2005-12-07 14:57:27 UTC
OK, its good to see that you can reproduce the bug. I was going to attach a
valgrind trace to prove the bug really is there. The code in auditd is simply
creating a pipe, forking, dup'ing the pipe to stdin, and then exec'ing the bash
script. It ocassionally writes to the pipe. Not sure how the differs from the
'|' operator.

Comment 7 Tim Waugh 2005-12-07 15:53:09 UTC
Ah, it might be to do with O_NONBLOCK, looking at the strace results.

Comment 9 Tim Waugh 2005-12-07 17:37:23 UTC
Okay, I've managed to reproduce it from a simplified test case.

Comment 10 Tim Waugh 2005-12-07 17:46:44 UTC
Created attachment 121988 [details]
nonblock.c

result=FAIL
ulimit -v 10240
./nonblock bash -c 'while :; do read -t 1 line; done'
if [ "$?" -eq 0 ]; then
  result=PASS
fi

Comment 11 Tim Waugh 2005-12-07 18:02:16 UTC
Created attachment 121989 [details]
bash-read-memleak.patch

Here's the fix for this particular case.  The 'find_or_make_array_variable'
case in your patch does look correct, but I can't quite work out how to
demonstrate that leak.	I'll mention it upstream.

Comment 12 Tim Waugh 2005-12-07 18:06:55 UTC
Reported upstream.

Comment 13 Tim Waugh 2005-12-08 12:01:49 UTC
The read-from-non-blocking-fd leak has been fixed in bash-3.0-40.

However, does auditd really need to give a non-blocking file descriptor to the
dispatcher process?  It means that bash will busy-loop when reading -- the shell
generally has no reason to use select().  I've filed bug #175267 for this.

Leaving this bug report open until I can get upstream feedback on the other
suspected leak.

Comment 14 Steve Grubb 2005-12-08 23:39:19 UTC
Tim, thanks for patching bash.

The audit daemon has to absolutely guarantee logging to disk. Dispatching events
are on a best effort basis hence the non-blocking descriptor. This is required
for meeting certification. The bash bug was discovered when I was doing some
troubleshooting since the audit dispatcher is still under development. I just
needed a quick and dirty script to detect something.

Comment 15 Tim Waugh 2005-12-09 09:20:07 UTC
Ah, okay.

Still no feedback from upstream regarding this patch, so keeping this open.

Comment 16 Tim Waugh 2006-02-13 12:54:57 UTC
I've prodded upstream about this again.


Note You need to log in before you can comment on or make changes to this bug.