diff options
author | Alan Modra <amodra@gmail.com> | 2022-11-11 13:43:42 +1030 |
---|---|---|
committer | Alan Modra <amodra@gmail.com> | 2022-11-11 18:05:36 +1030 |
commit | f7502dfe3f99d09fba2fc49f806ccc6b0a18c06d (patch) | |
tree | 2647f5d77d7515971d4ece107bafb5c4520920ac /bfd/compress.c | |
parent | d0e5049d8fa8e1994a42bb0296f72cc981b8ce8c (diff) | |
download | binutils-f7502dfe3f99d09fba2fc49f806ccc6b0a18c06d.zip binutils-f7502dfe3f99d09fba2fc49f806ccc6b0a18c06d.tar.gz binutils-f7502dfe3f99d09fba2fc49f806ccc6b0a18c06d.tar.bz2 |
PR28834, PR26946 sanity checking section size
This patch provides a new function to sanity check section sizes.
It's mostly extracted from what we had in bfd_get_full_section_contents
but also handles compressed debug sections.
Improvements are:
- section file offset is taken into account,
- added checks that a compressed section can be read from file.
The function is then used when handling multiple .debug_* sections
that need to be read into a single buffer, to sanity check sizes
before allocating the buffer.
PR 26946, PR 28834
* Makefile.am (LIBBFD_H_FILES): Add section.c.
* compress.c (bfd_get_full_section_contents): Move section size
sanity checks..
* section.c (_bfd_section_size_insane): ..to here. New function.
* dwarf2.c (read_section): Use _bfd_section_size_insane.
(_bfd_dwarf2_slurp_debug_info): Likewise.
* Makefile.in: Regenerate.
* libbfd.h: Regenerate.
Diffstat (limited to 'bfd/compress.c')
-rw-r--r-- | bfd/compress.c | 43 |
1 files changed, 14 insertions, 29 deletions
diff --git a/bfd/compress.c b/bfd/compress.c index 9608a0a..ad3feea 100644 --- a/bfd/compress.c +++ b/bfd/compress.c @@ -244,7 +244,7 @@ DESCRIPTION bool bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr) { - bfd_size_type sz; + bfd_size_type sz = bfd_get_section_limit_octets (abfd, sec); bfd_byte *p = *ptr; bool ret; bfd_size_type save_size; @@ -253,45 +253,30 @@ bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr) unsigned int compression_header_size; const unsigned int compress_status = sec->compress_status; - if (abfd->direction != write_direction && sec->rawsize != 0) - sz = sec->rawsize; - else - sz = sec->size; if (sz == 0) { *ptr = NULL; return true; } + if (p == NULL + && compress_status != COMPRESS_SECTION_DONE + && _bfd_section_size_insane (abfd, sec)) + { + /* PR 24708: Avoid attempts to allocate a ridiculous amount + of memory. */ + _bfd_error_handler + /* xgettext:c-format */ + (_("error: %pB(%pA) is too large (%#" PRIx64 " bytes)"), + abfd, sec, (uint64_t) sz); + return false; + } + switch (compress_status) { case COMPRESS_SECTION_NONE: if (p == NULL) { - ufile_ptr filesize = bfd_get_file_size (abfd); - if (filesize > 0 - && filesize < sz - && (bfd_section_flags (sec) & SEC_IN_MEMORY) == 0 - /* PR 24753: Linker created sections can be larger than - the file size, eg if they are being used to hold stubs. */ - && (bfd_section_flags (sec) & SEC_LINKER_CREATED) == 0 - /* PR 24753: Sections which have no content should also be - excluded as they contain no size on disk. */ - && (bfd_section_flags (sec) & SEC_HAS_CONTENTS) != 0 - /* The MMO file format supports its own special compression - technique, but it uses COMPRESS_SECTION_NONE when loading - a section's contents. */ - && bfd_get_flavour (abfd) != bfd_target_mmo_flavour) - { - /* PR 24708: Avoid attempts to allocate a ridiculous amount - of memory. */ - bfd_set_error (bfd_error_file_truncated); - _bfd_error_handler - /* xgettext:c-format */ - (_("error: %pB(%pA) section size (%#" PRIx64 " bytes) is larger than file size (%#" PRIx64 " bytes)"), - abfd, sec, (uint64_t) sz, (uint64_t) filesize); - return false; - } p = (bfd_byte *) bfd_malloc (sz); if (p == NULL) { |