diff options
author | Alan Modra <amodra@gmail.com> | 2015-11-18 22:12:23 +1030 |
---|---|---|
committer | Alan Modra <amodra@gmail.com> | 2015-11-18 22:16:24 +1030 |
commit | 4978e369fb75a8b7756bf4201668b2a9d9556286 (patch) | |
tree | fdeb0c2ed956f9b17c24e69efdf855efcc86be2a /bfd/archive.c | |
parent | 47daa70fe08c57aaafa6fe1a7e762072909d0f8f (diff) | |
download | gdb-4978e369fb75a8b7756bf4201668b2a9d9556286.zip gdb-4978e369fb75a8b7756bf4201668b2a9d9556286.tar.gz gdb-4978e369fb75a8b7756bf4201668b2a9d9556286.tar.bz2 |
Prevent looping in archives
PR 19256
* archive.c (bfd_generic_openr_next_archived_file): Don't allow
backward file movement via "negative" sizes.
* coff-alpha.c (alpha_ecoff_openr_next_archived_file): Likewise.
Diffstat (limited to 'bfd/archive.c')
-rw-r--r-- | bfd/archive.c | 24 |
1 files changed, 16 insertions, 8 deletions
diff --git a/bfd/archive.c b/bfd/archive.c index 1715474..b3d03d3 100644 --- a/bfd/archive.c +++ b/bfd/archive.c @@ -786,21 +786,29 @@ bfd_openr_next_archived_file (bfd *archive, bfd *last_file) bfd * bfd_generic_openr_next_archived_file (bfd *archive, bfd *last_file) { - file_ptr filestart; + ufile_ptr filestart; if (!last_file) filestart = bfd_ardata (archive)->first_file_filepos; else { - bfd_size_type size = arelt_size (last_file); - filestart = last_file->proxy_origin; if (! bfd_is_thin_archive (archive)) - filestart += size; - /* Pad to an even boundary... - Note that last_file->origin can be odd in the case of - BSD-4.4-style element with a long odd size. */ - filestart += filestart % 2; + { + bfd_size_type size = arelt_size (last_file); + + filestart += size; + /* Pad to an even boundary... + Note that last_file->origin can be odd in the case of + BSD-4.4-style element with a long odd size. */ + filestart += filestart % 2; + if (filestart <= last_file->proxy_origin) + { + /* Prevent looping. See PR19256. */ + bfd_set_error (bfd_error_malformed_archive); + return NULL; + } + } } return _bfd_get_elt_at_filepos (archive, filestart); |