diff options
author | Alan Modra <amodra@gmail.com> | 2019-09-02 16:13:05 +0930 |
---|---|---|
committer | Alan Modra <amodra@gmail.com> | 2019-09-05 11:33:34 +0930 |
commit | 89bdc77eabf5ede68322f6e47e003c1dc45b9ccb (patch) | |
tree | 87e650254fe116fdf69906ca003a0d8c34c491ac /bfd/opncls.c | |
parent | 809f9153986595498fbb59e547ea4e75a94a50f6 (diff) | |
download | gdb-89bdc77eabf5ede68322f6e47e003c1dc45b9ccb.zip gdb-89bdc77eabf5ede68322f6e47e003c1dc45b9ccb.tar.gz gdb-89bdc77eabf5ede68322f6e47e003c1dc45b9ccb.tar.bz2 |
PR24955, libbfd terminating program on out of memory
This patch fixes the worst of the cases where libbfd might terminate
a program due to calling xstrdup or xmalloc. I've also fixed some
error paths that didn't clean up properly.
PR 24955
* libbfd-in.h (bfd_strdup): New inline function.
* archive.c (_bfd_get_elt_at_filepos): Use bfd_strdup. Close
bfd on error.
* elfcode.h (_bfd_elf_bfd_from_remote_memory): Use bfd_strdup.
* opncls.c (bfd_fopen): Use bfd_strdup. Close fd and stream
on error.
(bfd_openstreamr): Use bfd_strdup.
(bfd_openr_iovec, bfd_openw, bfd_create): Likewise.
* plugin.c (try_load_plugin): Use bfd_malloc.
* libbfd.h: Regenerate.
Diffstat (limited to 'bfd/opncls.c')
-rw-r--r-- | bfd/opncls.c | 41 |
1 files changed, 35 insertions, 6 deletions
diff --git a/bfd/opncls.c b/bfd/opncls.c index b8cda41..07f89b9 100644 --- a/bfd/opncls.c +++ b/bfd/opncls.c @@ -223,6 +223,8 @@ bfd_fopen (const char *filename, const char *target, const char *mode, int fd) if (nbfd->iostream == NULL) { bfd_set_error (bfd_error_system_call); + if (fd != -1) + close (fd); _bfd_delete_bfd (nbfd); return NULL; } @@ -231,7 +233,13 @@ bfd_fopen (const char *filename, const char *target, const char *mode, int fd) /* PR 11983: Do not cache the original filename, but rather make a copy - the original might go away. */ - nbfd->filename = xstrdup (filename); + nbfd->filename = bfd_strdup (filename); + if (nbfd->filename == NULL) + { + fclose (nbfd->iostream); + _bfd_delete_bfd (nbfd); + return NULL; + } /* Figure out whether the user is opening the file for reading, writing, or both, by looking at the MODE argument. */ @@ -243,8 +251,9 @@ bfd_fopen (const char *filename, const char *target, const char *mode, int fd) else nbfd->direction = write_direction; - if (! bfd_cache_init (nbfd)) + if (!bfd_cache_init (nbfd)) { + fclose (nbfd->iostream); _bfd_delete_bfd (nbfd); return NULL; } @@ -398,7 +407,12 @@ bfd_openstreamr (const char *filename, const char *target, void *streamarg) nbfd->iostream = stream; /* PR 11983: Do not cache the original filename, but rather make a copy - the original might go away. */ - nbfd->filename = xstrdup (filename); + nbfd->filename = bfd_strdup (filename); + if (nbfd->filename == NULL) + { + _bfd_delete_bfd (nbfd); + return NULL; + } nbfd->direction = read_direction; if (! bfd_cache_init (nbfd)) @@ -594,7 +608,12 @@ bfd_openr_iovec (const char *filename, const char *target, /* PR 11983: Do not cache the original filename, but rather make a copy - the original might go away. */ - nbfd->filename = xstrdup (filename); + nbfd->filename = bfd_strdup (filename); + if (nbfd->filename == NULL) + { + _bfd_delete_bfd (nbfd); + return NULL; + } nbfd->direction = read_direction; /* `open_p (...)' would get expanded by an the open(2) syscall macro. */ @@ -661,7 +680,12 @@ bfd_openw (const char *filename, const char *target) /* PR 11983: Do not cache the original filename, but rather make a copy - the original might go away. */ - nbfd->filename = xstrdup (filename); + nbfd->filename = bfd_strdup (filename); + if (nbfd->filename == NULL) + { + _bfd_delete_bfd (nbfd); + return NULL; + } nbfd->direction = write_direction; if (bfd_open_file (nbfd) == NULL) @@ -801,7 +825,12 @@ bfd_create (const char *filename, bfd *templ) return NULL; /* PR 11983: Do not cache the original filename, but rather make a copy - the original might go away. */ - nbfd->filename = xstrdup (filename); + nbfd->filename = bfd_strdup (filename); + if (nbfd->filename == NULL) + { + _bfd_delete_bfd (nbfd); + return NULL; + } if (templ) nbfd->xvec = templ->xvec; nbfd->direction = no_direction; |