This is the mail archive of the
binutils@sourceware.org
mailing list for the binutils project.
bfd_get_full_section_contents memory leak, plus
- From: Tom Tromey <tromey at redhat dot com>
- To: Binutils Development <binutils at sourceware dot org>
- Date: Tue, 16 Oct 2012 21:12:10 -0600
- Subject: bfd_get_full_section_contents memory leak, plus
I noticed that bfd_get_full_section_contents has a memory leak. If you
set BFD_DECOMPRESS on the BFD, then use bfd_get_full_section_contents to
read a compressed section, the uncompressed section data will be
malloc'd and stored as section->contents -- but nothing ever frees this.
My fix for this (appended) is to allocate the uncompressed data on the
BFD's objalloc.
While looking into this I thought that it would be good to also set
SEC_IN_MEMORY in this case. I'm less sure of this change.
However, what I'd really like here is a way for gdb to better control
the caching. Right now, if gdb uses bfd_get_full_section_contents, then
in the compressed case we will have two copies of the section data in
memory -- needlessly wasteful.
Any suggestions for how you would like this to be done? I could either
add a new function, to be used in lieu of bfd_get_full_section_contents;
or remove the caching entirely; or make a new sentinel initialization
value for the 'ptr' argument to indicate that the function should always
cache the data and never make a copy.
There is a gdb patch series that is blocked on this, so I'd appreciate a
timely answer.
thanks,
Tom
* compress.c (bfd_get_full_section_contents): Use bfd_alloc
and bfd_release for allocate uncompressed data. Set
SEC_IN_MEMORY.
diff --git a/bfd/compress.c b/bfd/compress.c
index 52c884c..ca71261 100644
--- a/bfd/compress.c
+++ b/bfd/compress.c
@@ -220,7 +220,7 @@ bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr)
if (!ret)
goto fail_compressed;
- uncompressed_buffer = (bfd_byte *) bfd_malloc (uncompressed_size);
+ uncompressed_buffer = (bfd_byte *) bfd_alloc (abfd, uncompressed_size);
if (uncompressed_buffer == NULL)
goto fail_compressed;
@@ -228,13 +228,14 @@ bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr)
uncompressed_buffer, uncompressed_size))
{
bfd_set_error (bfd_error_bad_value);
- free (uncompressed_buffer);
+ bfd_release (abfd, uncompressed_buffer);
fail_compressed:
free (compressed_buffer);
return FALSE;
}
free (compressed_buffer);
+ sec->flags |= SEC_IN_MEMORY;
sec->contents = uncompressed_buffer;
sec->compress_status = COMPRESS_SECTION_DONE;
/* Fall thru */