Home | History | Annotate | Line # | Download | only in bfd
compress.c revision 1.7
      1 /* Compressed section support (intended for debug sections).
      2    Copyright (C) 2008-2017 Free Software Foundation, Inc.
      3 
      4    This file is part of BFD, the Binary File Descriptor library.
      5 
      6    This program is free software; you can redistribute it and/or modify
      7    it under the terms of the GNU General Public License as published by
      8    the Free Software Foundation; either version 3 of the License, or
      9    (at your option) any later version.
     10 
     11    This program is distributed in the hope that it will be useful,
     12    but WITHOUT ANY WARRANTY; without even the implied warranty of
     13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     14    GNU General Public License for more details.
     15 
     16    You should have received a copy of the GNU General Public License
     17    along with this program; if not, write to the Free Software
     18    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     19    MA 02110-1301, USA.  */
     20 
     21 #include "sysdep.h"
     22 #include <zlib.h>
     23 #include "bfd.h"
     24 #include "libbfd.h"
     25 #include "safe-ctype.h"
     26 
     27 #define MAX_COMPRESSION_HEADER_SIZE 24
     28 
     29 static bfd_boolean
     30 decompress_contents (bfd_byte *compressed_buffer,
     31 		     bfd_size_type compressed_size,
     32 		     bfd_byte *uncompressed_buffer,
     33 		     bfd_size_type uncompressed_size)
     34 {
     35   z_stream strm;
     36   int rc;
     37 
     38   /* It is possible the section consists of several compressed
     39      buffers concatenated together, so we uncompress in a loop.  */
     40   /* PR 18313: The state field in the z_stream structure is supposed
     41      to be invisible to the user (ie us), but some compilers will
     42      still complain about it being used without initialisation.  So
     43      we first zero the entire z_stream structure and then set the fields
     44      that we need.  */
     45   memset (& strm, 0, sizeof strm);
     46   strm.avail_in = compressed_size;
     47   strm.next_in = (Bytef*) compressed_buffer;
     48   strm.avail_out = uncompressed_size;
     49 
     50   BFD_ASSERT (Z_OK == 0);
     51   rc = inflateInit (&strm);
     52   while (strm.avail_in > 0 && strm.avail_out > 0)
     53     {
     54       if (rc != Z_OK)
     55 	break;
     56       strm.next_out = ((Bytef*) uncompressed_buffer
     57                        + (uncompressed_size - strm.avail_out));
     58       rc = inflate (&strm, Z_FINISH);
     59       if (rc != Z_STREAM_END)
     60 	break;
     61       rc = inflateReset (&strm);
     62     }
     63   rc |= inflateEnd (&strm);
     64   return rc == Z_OK && strm.avail_out == 0;
     65 }
     66 
     67 /* Compress data of the size specified in @var{uncompressed_size}
     68    and pointed to by @var{uncompressed_buffer} using zlib and store
     69    as the contents field.  This function assumes the contents
     70    field was allocated using bfd_malloc() or equivalent.
     71 
     72    Return the uncompressed size if the full section contents is
     73    compressed successfully.  Otherwise return 0.  */
     74 
     75 static bfd_size_type
     76 bfd_compress_section_contents (bfd *abfd, sec_ptr sec,
     77 			       bfd_byte *uncompressed_buffer,
     78 			       bfd_size_type uncompressed_size)
     79 {
     80   uLong compressed_size;
     81   bfd_byte *buffer;
     82   bfd_size_type buffer_size;
     83   bfd_boolean decompress;
     84   int zlib_size = 0;
     85   int orig_compression_header_size;
     86   bfd_size_type orig_uncompressed_size;
     87   int header_size = bfd_get_compression_header_size (abfd, NULL);
     88   bfd_boolean compressed
     89     = bfd_is_section_compressed_with_header (abfd, sec,
     90 					     &orig_compression_header_size,
     91 					     &orig_uncompressed_size);
     92 
     93   /* Either ELF compression header or the 12-byte, "ZLIB" + 8-byte size,
     94      overhead in .zdebug* section.  */
     95   if (!header_size)
     96      header_size = 12;
     97 
     98   if (compressed)
     99     {
    100       /* We shouldn't decompress unsupported compressed section.  */
    101       if (orig_compression_header_size < 0)
    102 	abort ();
    103 
    104       /* Different compression schemes.  Just move the compressed section
    105 	 contents to the right position. */
    106       if (orig_compression_header_size == 0)
    107 	{
    108 	  /* Convert it from .zdebug* section.  Get the uncompressed
    109 	     size first.  We need to substract the 12-byte overhead in
    110 	     .zdebug* section.  Set orig_compression_header_size to
    111 	     the 12-bye overhead.  */
    112 	  orig_compression_header_size = 12;
    113 	  zlib_size = uncompressed_size - 12;
    114 	}
    115       else
    116 	{
    117 	  /* Convert it to .zdebug* section.  */
    118 	  zlib_size = uncompressed_size - orig_compression_header_size;
    119 	}
    120 
    121       /* Add the header size.  */
    122       compressed_size = zlib_size + header_size;
    123     }
    124   else
    125     compressed_size = compressBound (uncompressed_size) + header_size;
    126 
    127   /* Uncompress if it leads to smaller size.  */
    128   if (compressed && compressed_size > orig_uncompressed_size)
    129     {
    130       decompress = TRUE;
    131       buffer_size = orig_uncompressed_size;
    132     }
    133   else
    134     {
    135       decompress = FALSE;
    136       buffer_size = compressed_size;
    137     }
    138   buffer = (bfd_byte *) bfd_alloc (abfd, buffer_size);
    139   if (buffer == NULL)
    140     return 0;
    141 
    142   if (compressed)
    143     {
    144       sec->size = orig_uncompressed_size;
    145       if (decompress)
    146 	{
    147 	  if (!decompress_contents (uncompressed_buffer
    148 				    + orig_compression_header_size,
    149 				    zlib_size, buffer, buffer_size))
    150 	    {
    151 	      bfd_set_error (bfd_error_bad_value);
    152 	      bfd_release (abfd, buffer);
    153 	      return 0;
    154 	    }
    155 	  free (uncompressed_buffer);
    156 	  sec->contents = buffer;
    157 	  sec->compress_status = COMPRESS_SECTION_DONE;
    158 	  return orig_uncompressed_size;
    159 	}
    160       else
    161 	{
    162 	  bfd_update_compression_header (abfd, buffer, sec);
    163 	  memmove (buffer + header_size,
    164 		   uncompressed_buffer + orig_compression_header_size,
    165 		   zlib_size);
    166 	}
    167     }
    168   else
    169     {
    170       if (compress ((Bytef*) buffer + header_size,
    171 		    &compressed_size,
    172 		    (const Bytef*) uncompressed_buffer,
    173 		    uncompressed_size) != Z_OK)
    174 	{
    175 	  bfd_release (abfd, buffer);
    176 	  bfd_set_error (bfd_error_bad_value);
    177 	  return 0;
    178 	}
    179 
    180       compressed_size += header_size;
    181       /* PR binutils/18087: If compression didn't make the section smaller,
    182 	 just keep it uncompressed.  */
    183       if (compressed_size < uncompressed_size)
    184 	bfd_update_compression_header (abfd, buffer, sec);
    185       else
    186 	{
    187 	  /* NOTE: There is a small memory leak here since
    188 	     uncompressed_buffer is malloced and won't be freed.  */
    189 	  bfd_release (abfd, buffer);
    190 	  sec->contents = uncompressed_buffer;
    191 	  sec->compress_status = COMPRESS_SECTION_NONE;
    192 	  return uncompressed_size;
    193 	}
    194     }
    195 
    196   free (uncompressed_buffer);
    197   sec->contents = buffer;
    198   sec->size = compressed_size;
    199   sec->compress_status = COMPRESS_SECTION_DONE;
    200 
    201   return uncompressed_size;
    202 }
    203 
    204 /*
    205 FUNCTION
    206 	bfd_get_full_section_contents
    207 
    208 SYNOPSIS
    209 	bfd_boolean bfd_get_full_section_contents
    210 	  (bfd *abfd, asection *section, bfd_byte **ptr);
    211 
    212 DESCRIPTION
    213 	Read all data from @var{section} in BFD @var{abfd}, decompress
    214 	if needed, and store in @var{*ptr}.  If @var{*ptr} is NULL,
    215 	return @var{*ptr} with memory malloc'd by this function.
    216 
    217 	Return @code{TRUE} if the full section contents is retrieved
    218 	successfully.  If the section has no contents then this function
    219 	returns @code{TRUE} but @var{*ptr} is set to NULL.
    220 */
    221 
    222 bfd_boolean
    223 bfd_get_full_section_contents (bfd *abfd, sec_ptr sec, bfd_byte **ptr)
    224 {
    225   bfd_size_type sz;
    226   bfd_byte *p = *ptr;
    227   bfd_boolean ret;
    228   bfd_size_type save_size;
    229   bfd_size_type save_rawsize;
    230   bfd_byte *compressed_buffer;
    231   unsigned int compression_header_size;
    232 
    233   if (abfd->direction != write_direction && sec->rawsize != 0)
    234     sz = sec->rawsize;
    235   else
    236     sz = sec->size;
    237   if (sz == 0)
    238     {
    239       *ptr = NULL;
    240       return TRUE;
    241     }
    242 
    243   switch (sec->compress_status)
    244     {
    245     case COMPRESS_SECTION_NONE:
    246       if (p == NULL)
    247 	{
    248 	  p = (bfd_byte *) bfd_malloc (sz);
    249 	  if (p == NULL)
    250 	    {
    251 	      /* PR 20801: Provide a more helpful error message.  */
    252 	      if (bfd_get_error () == bfd_error_no_memory)
    253 		_bfd_error_handler
    254 		  /* xgettext:c-format */
    255 		  (_("error: %B(%A) is too large (%#lx bytes)"),
    256 		  abfd, sec, (long) sz);
    257 	    return FALSE;
    258 	    }
    259 	}
    260 
    261       if (!bfd_get_section_contents (abfd, sec, p, 0, sz))
    262 	{
    263 	  if (*ptr != p)
    264 	    free (p);
    265 	  return FALSE;
    266 	}
    267       *ptr = p;
    268       return TRUE;
    269 
    270     case DECOMPRESS_SECTION_SIZED:
    271       /* Read in the full compressed section contents.  */
    272       compressed_buffer = (bfd_byte *) bfd_malloc (sec->compressed_size);
    273       if (compressed_buffer == NULL)
    274 	return FALSE;
    275       save_rawsize = sec->rawsize;
    276       save_size = sec->size;
    277       /* Clear rawsize, set size to compressed size and set compress_status
    278 	 to COMPRESS_SECTION_NONE.  If the compressed size is bigger than
    279 	 the uncompressed size, bfd_get_section_contents will fail.  */
    280       sec->rawsize = 0;
    281       sec->size = sec->compressed_size;
    282       sec->compress_status = COMPRESS_SECTION_NONE;
    283       ret = bfd_get_section_contents (abfd, sec, compressed_buffer,
    284 				      0, sec->compressed_size);
    285       /* Restore rawsize and size.  */
    286       sec->rawsize = save_rawsize;
    287       sec->size = save_size;
    288       sec->compress_status = DECOMPRESS_SECTION_SIZED;
    289       if (!ret)
    290 	goto fail_compressed;
    291 
    292       if (p == NULL)
    293 	p = (bfd_byte *) bfd_malloc (sz);
    294       if (p == NULL)
    295 	goto fail_compressed;
    296 
    297       compression_header_size = bfd_get_compression_header_size (abfd, sec);
    298       if (compression_header_size == 0)
    299 	/* Set header size to the zlib header size if it is a
    300 	   SHF_COMPRESSED section.  */
    301 	compression_header_size = 12;
    302       if (!decompress_contents (compressed_buffer + compression_header_size,
    303 				sec->compressed_size - compression_header_size, p, sz))
    304 	{
    305 	  bfd_set_error (bfd_error_bad_value);
    306 	  if (p != *ptr)
    307 	    free (p);
    308 	fail_compressed:
    309 	  free (compressed_buffer);
    310 	  return FALSE;
    311 	}
    312 
    313       free (compressed_buffer);
    314       *ptr = p;
    315       return TRUE;
    316 
    317     case COMPRESS_SECTION_DONE:
    318       if (sec->contents == NULL)
    319 	return FALSE;
    320       if (p == NULL)
    321 	{
    322 	  p = (bfd_byte *) bfd_malloc (sz);
    323 	  if (p == NULL)
    324 	    return FALSE;
    325 	  *ptr = p;
    326 	}
    327       /* PR 17512; file: 5bc29788.  */
    328       if (p != sec->contents)
    329 	memcpy (p, sec->contents, sz);
    330       return TRUE;
    331 
    332     default:
    333       abort ();
    334     }
    335 }
    336 
    337 /*
    338 FUNCTION
    339 	bfd_cache_section_contents
    340 
    341 SYNOPSIS
    342 	void bfd_cache_section_contents
    343 	  (asection *sec, void *contents);
    344 
    345 DESCRIPTION
    346 	Stash @var(contents) so any following reads of @var(sec) do
    347 	not need to decompress again.
    348 */
    349 
    350 void
    351 bfd_cache_section_contents (asection *sec, void *contents)
    352 {
    353   if (sec->compress_status == DECOMPRESS_SECTION_SIZED)
    354     sec->compress_status = COMPRESS_SECTION_DONE;
    355   sec->contents = contents;
    356   sec->flags |= SEC_IN_MEMORY;
    357 }
    358 
    359 /*
    360 FUNCTION
    361 	bfd_is_section_compressed_with_header
    362 
    363 SYNOPSIS
    364 	bfd_boolean bfd_is_section_compressed_with_header
    365 	  (bfd *abfd, asection *section,
    366 	  int *compression_header_size_p,
    367 	  bfd_size_type *uncompressed_size_p);
    368 
    369 DESCRIPTION
    370 	Return @code{TRUE} if @var{section} is compressed.  Compression
    371 	header size is returned in @var{compression_header_size_p} and
    372 	uncompressed size is returned in @var{uncompressed_size_p}.  If
    373 	compression is unsupported, compression header size is returned
    374 	with -1 and uncompressed size is returned with 0.
    375 */
    376 
    377 bfd_boolean
    378 bfd_is_section_compressed_with_header (bfd *abfd, sec_ptr sec,
    379 				       int *compression_header_size_p,
    380 				       bfd_size_type *uncompressed_size_p)
    381 {
    382   bfd_byte header[MAX_COMPRESSION_HEADER_SIZE];
    383   int compression_header_size;
    384   int header_size;
    385   unsigned int saved = sec->compress_status;
    386   bfd_boolean compressed;
    387 
    388   compression_header_size = bfd_get_compression_header_size (abfd, sec);
    389   if (compression_header_size > MAX_COMPRESSION_HEADER_SIZE)
    390     abort ();
    391   header_size = compression_header_size ? compression_header_size : 12;
    392 
    393   /* Don't decompress the section.  */
    394   sec->compress_status = COMPRESS_SECTION_NONE;
    395 
    396   /* Read the header.  */
    397   if (bfd_get_section_contents (abfd, sec, header, 0, header_size))
    398     {
    399       if (compression_header_size == 0)
    400         /* In this case, it should be "ZLIB" followed by the uncompressed
    401 	   section size, 8 bytes in big-endian order.  */
    402 	compressed = CONST_STRNEQ ((char*) header , "ZLIB");
    403       else
    404 	compressed = TRUE;
    405     }
    406   else
    407     compressed = FALSE;
    408 
    409   *uncompressed_size_p = sec->size;
    410   if (compressed)
    411     {
    412       if (compression_header_size != 0)
    413 	{
    414 	  if (!bfd_check_compression_header (abfd, header, sec,
    415 					     uncompressed_size_p))
    416 	    compression_header_size = -1;
    417 	}
    418       /* Check for the pathalogical case of a debug string section that
    419 	 contains the string ZLIB.... as the first entry.  We assume that
    420 	 no uncompressed .debug_str section would ever be big enough to
    421 	 have the first byte of its (big-endian) size be non-zero.  */
    422       else if (strcmp (sec->name, ".debug_str") == 0
    423 	       && ISPRINT (header[4]))
    424 	compressed = FALSE;
    425       else
    426 	*uncompressed_size_p = bfd_getb64 (header + 4);
    427     }
    428 
    429   /* Restore compress_status.  */
    430   sec->compress_status = saved;
    431   *compression_header_size_p = compression_header_size;
    432   return compressed;
    433 }
    434 
    435 /*
    436 FUNCTION
    437 	bfd_is_section_compressed
    438 
    439 SYNOPSIS
    440 	bfd_boolean bfd_is_section_compressed
    441 	  (bfd *abfd, asection *section);
    442 
    443 DESCRIPTION
    444 	Return @code{TRUE} if @var{section} is compressed.
    445 */
    446 
    447 bfd_boolean
    448 bfd_is_section_compressed (bfd *abfd, sec_ptr sec)
    449 {
    450   int compression_header_size;
    451   bfd_size_type uncompressed_size;
    452   return (bfd_is_section_compressed_with_header (abfd, sec,
    453 						 &compression_header_size,
    454 						 &uncompressed_size)
    455 	  && compression_header_size >= 0
    456 	  && uncompressed_size > 0);
    457 }
    458 
    459 /*
    460 FUNCTION
    461 	bfd_init_section_decompress_status
    462 
    463 SYNOPSIS
    464 	bfd_boolean bfd_init_section_decompress_status
    465 	  (bfd *abfd, asection *section);
    466 
    467 DESCRIPTION
    468 	Record compressed section size, update section size with
    469 	decompressed size and set compress_status to
    470 	DECOMPRESS_SECTION_SIZED.
    471 
    472 	Return @code{FALSE} if the section is not a valid compressed
    473 	section.  Otherwise, return @code{TRUE}.
    474 */
    475 
    476 bfd_boolean
    477 bfd_init_section_decompress_status (bfd *abfd, sec_ptr sec)
    478 {
    479   bfd_byte header[MAX_COMPRESSION_HEADER_SIZE];
    480   int compression_header_size;
    481   int header_size;
    482   bfd_size_type uncompressed_size;
    483 
    484   compression_header_size = bfd_get_compression_header_size (abfd, sec);
    485   if (compression_header_size > MAX_COMPRESSION_HEADER_SIZE)
    486     abort ();
    487   header_size = compression_header_size ? compression_header_size : 12;
    488 
    489   /* Read the header.  */
    490   if (sec->rawsize != 0
    491       || sec->contents != NULL
    492       || sec->compress_status != COMPRESS_SECTION_NONE
    493       || !bfd_get_section_contents (abfd, sec, header, 0, header_size))
    494     {
    495       bfd_set_error (bfd_error_invalid_operation);
    496       return FALSE;
    497     }
    498 
    499   if (compression_header_size == 0)
    500     {
    501       /* In this case, it should be "ZLIB" followed by the uncompressed
    502 	 section size, 8 bytes in big-endian order.  */
    503       if (! CONST_STRNEQ ((char*) header, "ZLIB"))
    504 	{
    505 	  bfd_set_error (bfd_error_wrong_format);
    506 	  return FALSE;
    507 	}
    508       uncompressed_size = bfd_getb64 (header + 4);
    509     }
    510   else if (!bfd_check_compression_header (abfd, header, sec,
    511 					 &uncompressed_size))
    512     {
    513       bfd_set_error (bfd_error_wrong_format);
    514       return FALSE;
    515     }
    516 
    517   sec->compressed_size = sec->size;
    518   sec->size = uncompressed_size;
    519   sec->compress_status = DECOMPRESS_SECTION_SIZED;
    520 
    521   return TRUE;
    522 }
    523 
    524 /*
    525 FUNCTION
    526 	bfd_init_section_compress_status
    527 
    528 SYNOPSIS
    529 	bfd_boolean bfd_init_section_compress_status
    530 	  (bfd *abfd, asection *section);
    531 
    532 DESCRIPTION
    533 	If open for read, compress section, update section size with
    534 	compressed size and set compress_status to COMPRESS_SECTION_DONE.
    535 
    536 	Return @code{FALSE} if the section is not a valid compressed
    537 	section.  Otherwise, return @code{TRUE}.
    538 */
    539 
    540 bfd_boolean
    541 bfd_init_section_compress_status (bfd *abfd, sec_ptr sec)
    542 {
    543   bfd_size_type uncompressed_size;
    544   bfd_byte *uncompressed_buffer;
    545   bfd_boolean ret;
    546 
    547   /* Error if not opened for read.  */
    548   if (abfd->direction != read_direction
    549       || sec->size == 0
    550       || sec->rawsize != 0
    551       || sec->contents != NULL
    552       || sec->compress_status != COMPRESS_SECTION_NONE)
    553     {
    554       bfd_set_error (bfd_error_invalid_operation);
    555       return FALSE;
    556     }
    557 
    558   /* Read in the full section contents and compress it.  */
    559   uncompressed_size = sec->size;
    560   uncompressed_buffer = (bfd_byte *) bfd_malloc (uncompressed_size);
    561   if (!bfd_get_section_contents (abfd, sec, uncompressed_buffer,
    562 				 0, uncompressed_size))
    563     ret = FALSE;
    564   else
    565     {
    566       uncompressed_size = bfd_compress_section_contents (abfd, sec,
    567 							 uncompressed_buffer,
    568 							 uncompressed_size);
    569       ret = uncompressed_size != 0;
    570     }
    571 
    572   return ret;
    573 }
    574 
    575 /*
    576 FUNCTION
    577 	bfd_compress_section
    578 
    579 SYNOPSIS
    580 	bfd_boolean bfd_compress_section
    581 	  (bfd *abfd, asection *section, bfd_byte *uncompressed_buffer);
    582 
    583 DESCRIPTION
    584 	If open for write, compress section, update section size with
    585 	compressed size and set compress_status to COMPRESS_SECTION_DONE.
    586 
    587 	Return @code{FALSE} if compression fail.  Otherwise, return
    588 	@code{TRUE}.
    589 */
    590 
    591 bfd_boolean
    592 bfd_compress_section (bfd *abfd, sec_ptr sec, bfd_byte *uncompressed_buffer)
    593 {
    594   bfd_size_type uncompressed_size = sec->size;
    595 
    596   /* Error if not opened for write.  */
    597   if (abfd->direction != write_direction
    598       || uncompressed_size == 0
    599       || uncompressed_buffer == NULL
    600       || sec->contents != NULL
    601       || sec->compressed_size != 0
    602       || sec->compress_status != COMPRESS_SECTION_NONE)
    603     {
    604       bfd_set_error (bfd_error_invalid_operation);
    605       return FALSE;
    606     }
    607 
    608   /* Compress it.  */
    609   return bfd_compress_section_contents (abfd, sec, uncompressed_buffer,
    610 					uncompressed_size) != 0;
    611 }
    612