X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=bfd%2Fsom.c;h=d53a3b90b0244fa703955045489144d1190cd2df;hb=13835d88dc51497b9bd68dc1f394ca0de099a380;hp=8575c891a4734841d803cc8da65359a9bef3ab85;hpb=7dba9362c172f1073487536eb137feb2da30b0ff;p=binutils-gdb.git diff --git a/bfd/som.c b/bfd/som.c index 8575c891a47..d53a3b90b02 100644 --- a/bfd/som.c +++ b/bfd/som.c @@ -1,5 +1,5 @@ /* bfd back-end for HP PA-RISC SOM objects. - Copyright (C) 1990-2017 Free Software Foundation, Inc. + Copyright (C) 1990-2022 Free Software Foundation, Inc. Contributed by the Center for Software Science at the University of Utah. @@ -22,7 +22,6 @@ 02110-1301, USA. */ #include "sysdep.h" -#include "alloca-conf.h" #include "bfd.h" #include "libiberty.h" #include "libbfd.h" @@ -33,12 +32,12 @@ static bfd_reloc_status_type hppa_som_reloc (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **); -static bfd_boolean som_mkobject (bfd *); -static bfd_boolean som_is_space (asection *); -static bfd_boolean som_is_subspace (asection *); +static bool som_mkobject (bfd *); +static bool som_is_space (asection *); +static bool som_is_subspace (asection *); static int compare_subspaces (const void *, const void *); -static unsigned long som_compute_checksum (struct som_external_header *); -static bfd_boolean som_build_and_write_symbol_table (bfd *); +static uint32_t som_compute_checksum (struct som_external_header *); +static bool som_build_and_write_symbol_table (bfd *); static unsigned int som_slurp_symbol_table (bfd *); /* Magic not defined in standard HP-UX header files until 8.0. */ @@ -114,7 +113,7 @@ static unsigned int som_slurp_symbol_table (bfd *); Note one side effect of using a R_PREV_FIXUP is the relocation that is being repeated moves to the front of the queue. */ -struct reloc_queue +static struct reloc_queue { unsigned char *reloc; unsigned int size; @@ -637,7 +636,7 @@ static const int comp3_opcodes[] = #endif #define SOM_HOWTO(TYPE, NAME) \ - HOWTO(TYPE, 0, 0, 32, FALSE, 0, 0, hppa_som_reloc, NAME, FALSE, 0, 0, FALSE) + HOWTO(TYPE, 0, 0, 32, false, 0, 0, hppa_som_reloc, NAME, false, 0, 0, false) static reloc_howto_type som_hppa_howto_table[] = { @@ -1425,7 +1424,7 @@ hppa_som_gen_reloc_type (bfd *abfd, /* The difference of two symbols needs *very* special handling. */ if (sym_diff) { - bfd_size_type amt = sizeof (int); + size_t amt = sizeof (int); final_types[0] = bfd_alloc (abfd, amt); final_types[1] = bfd_alloc (abfd, amt); @@ -1509,7 +1508,7 @@ hppa_som_gen_reloc_type (bfd *abfd, /* The difference of two symbols needs *very* special handling. */ if (sym_diff) { - bfd_size_type amt = sizeof (int); + size_t amt = sizeof (int); final_types[0] = bfd_alloc (abfd, amt); final_types[1] = bfd_alloc (abfd, amt); @@ -1548,7 +1547,7 @@ hppa_som_gen_reloc_type (bfd *abfd, /* If we have short and long pcrel modes, then generate the proper mode selector, then the pcrel relocation. Redundant selectors will be eliminated as the relocs are sized and emitted. */ - bfd_size_type amt = sizeof (int); + size_t amt = sizeof (int); final_types[0] = bfd_alloc (abfd, amt); if (!final_types[0]) @@ -1601,7 +1600,7 @@ som_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED, static void som_swap_clock_in (struct som_external_clock *src, - struct som_clock *dst) + struct som_clock *dst) { dst->secs = bfd_getb32 (src->secs); dst->nanosecs = bfd_getb32 (src->nanosecs); @@ -1609,7 +1608,7 @@ som_swap_clock_in (struct som_external_clock *src, static void som_swap_clock_out (struct som_clock *src, - struct som_external_clock *dst) + struct som_external_clock *dst) { bfd_putb32 (src->secs, dst->secs); bfd_putb32 (src->nanosecs, dst->nanosecs); @@ -1617,7 +1616,7 @@ som_swap_clock_out (struct som_clock *src, static void som_swap_header_in (struct som_external_header *src, - struct som_header *dst) + struct som_header *dst) { dst->system_id = bfd_getb16 (src->system_id); dst->a_magic = bfd_getb16 (src->a_magic); @@ -1655,7 +1654,7 @@ som_swap_header_in (struct som_external_header *src, static void som_swap_header_out (struct som_header *src, - struct som_external_header *dst) + struct som_external_header *dst) { bfd_putb16 (src->system_id, dst->system_id); bfd_putb16 (src->a_magic, dst->a_magic); @@ -1693,7 +1692,7 @@ som_swap_header_out (struct som_header *src, static void som_swap_space_dictionary_in (struct som_external_space_dictionary_record *src, - struct som_space_dictionary_record *dst) + struct som_space_dictionary_record *dst) { unsigned int flags; @@ -1718,7 +1717,7 @@ som_swap_space_dictionary_in (struct som_external_space_dictionary_record *src, static void som_swap_space_dictionary_out (struct som_space_dictionary_record *src, - struct som_external_space_dictionary_record *dst) + struct som_external_space_dictionary_record *dst) { unsigned int flags; @@ -1831,7 +1830,7 @@ som_swap_subspace_dictionary_record_out static void som_swap_aux_id_in (struct som_external_aux_id *src, - struct som_aux_id *dst) + struct som_aux_id *dst) { unsigned int flags = bfd_getb32 (src->flags); @@ -1845,7 +1844,7 @@ som_swap_aux_id_in (struct som_external_aux_id *src, static void som_swap_aux_id_out (struct som_aux_id *src, - struct som_external_aux_id *dst) + struct som_external_aux_id *dst) { unsigned int flags = 0; @@ -1864,7 +1863,7 @@ som_swap_aux_id_out (struct som_aux_id *src, static void som_swap_string_auxhdr_out (struct som_string_auxhdr *src, - struct som_external_string_auxhdr *dst) + struct som_external_string_auxhdr *dst) { som_swap_aux_id_out (&src->header_id, &dst->header_id); bfd_putb32 (src->string_length, dst->string_length); @@ -1872,7 +1871,7 @@ som_swap_string_auxhdr_out (struct som_string_auxhdr *src, static void som_swap_compilation_unit_out (struct som_compilation_unit *src, - struct som_external_compilation_unit *dst) + struct som_external_compilation_unit *dst) { bfd_putb32 (src->name.strx, dst->name); bfd_putb32 (src->language_name.strx, dst->language_name); @@ -1885,7 +1884,7 @@ som_swap_compilation_unit_out (struct som_compilation_unit *src, static void som_swap_exec_auxhdr_in (struct som_external_exec_auxhdr *src, - struct som_exec_auxhdr *dst) + struct som_exec_auxhdr *dst) { som_swap_aux_id_in (&src->som_auxhdr, &dst->som_auxhdr); dst->exec_tsize = bfd_getb32 (src->exec_tsize); @@ -1902,7 +1901,7 @@ som_swap_exec_auxhdr_in (struct som_external_exec_auxhdr *src, static void som_swap_exec_auxhdr_out (struct som_exec_auxhdr *src, - struct som_external_exec_auxhdr *dst) + struct som_external_exec_auxhdr *dst) { som_swap_aux_id_out (&src->som_auxhdr, &dst->som_auxhdr); bfd_putb32 (src->exec_tsize, dst->exec_tsize); @@ -1919,7 +1918,7 @@ som_swap_exec_auxhdr_out (struct som_exec_auxhdr *src, static void som_swap_lst_header_in (struct som_external_lst_header *src, - struct som_lst_header *dst) + struct som_lst_header *dst) { dst->system_id = bfd_getb16 (src->system_id); dst->a_magic = bfd_getb16 (src->a_magic); @@ -1945,7 +1944,7 @@ som_swap_lst_header_in (struct som_external_lst_header *src, /* Perform some initialization for an object. Save results of this initialization in the BFD. */ -static const bfd_target * +static bfd_cleanup som_object_setup (bfd *abfd, struct som_header *file_hdrp, struct som_exec_auxhdr *aux_hdrp, @@ -2031,12 +2030,12 @@ som_object_setup (bfd *abfd, || (aux_hdrp->exec_entry & 0x3) != 0 || ! found) { - bfd_get_start_address (abfd) = aux_hdrp->exec_flags; + abfd->start_address = aux_hdrp->exec_flags; obj_som_exec_data (abfd)->exec_flags = aux_hdrp->exec_entry; } else { - bfd_get_start_address (abfd) = aux_hdrp->exec_entry + current_offset; + abfd->start_address = aux_hdrp->exec_entry + current_offset; obj_som_exec_data (abfd)->exec_flags = aux_hdrp->exec_flags; } } @@ -2044,7 +2043,7 @@ som_object_setup (bfd *abfd, obj_som_exec_data (abfd)->version_id = file_hdrp->version_id; bfd_default_set_arch_mach (abfd, bfd_arch_hppa, pa10); - bfd_get_symcount (abfd) = file_hdrp->symbol_total; + abfd->symcount = file_hdrp->symbol_total; /* Initialize the saved symbol table and string table to NULL. Save important offsets and sizes from the SOM header into @@ -2060,7 +2059,7 @@ som_object_setup (bfd *abfd, + current_offset); obj_som_exec_data (abfd)->system_id = file_hdrp->system_id; - return abfd->xvec; + return _bfd_no_cleanup; } /* Convert all of the space and subspace info into BFD sections. Each space @@ -2069,29 +2068,33 @@ som_object_setup (bfd *abfd, BFD sections which correspond to spaces will overlap the sections for the associated subspaces. */ -static bfd_boolean +static bool setup_sections (bfd *abfd, struct som_header *file_hdr, unsigned long current_offset) { - char *space_strings; + char *space_strings = NULL; unsigned int space_index, i; unsigned int total_subspaces = 0; asection **subspace_sections = NULL; asection *section; - bfd_size_type amt; + size_t amt; /* First, read in space names. */ amt = file_hdr->space_strings_size; - space_strings = bfd_malloc (amt); - if (!space_strings && amt != 0) - goto error_return; - + if (amt == (size_t) -1) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } if (bfd_seek (abfd, current_offset + file_hdr->space_strings_location, SEEK_SET) != 0) goto error_return; - if (bfd_bread (space_strings, amt, abfd) != amt) + space_strings = (char *) _bfd_malloc_and_read (abfd, amt + 1, amt); + if (space_strings == NULL) goto error_return; + /* Make sure that the string table is NUL terminated. */ + space_strings[amt] = 0; /* Loop over all of the space dictionaries, building up sections. */ for (space_index = 0; space_index < file_hdr->space_total; space_index++) @@ -2119,6 +2122,9 @@ setup_sections (bfd *abfd, som_swap_space_dictionary_in (&ext_space, &space); /* Setup the space name string. */ + if (space.name >= file_hdr->space_strings_size) + goto error_return; + space_name = space.name + space_strings; /* Make a section out of it. */ @@ -2180,16 +2186,19 @@ setup_sections (bfd *abfd, subspace_index++) { asection *subspace_asect; - char *subspace_name; + char *subspace_name; /* Read in the next subspace. */ amt = sizeof ext_subspace; if (bfd_bread (&ext_subspace, amt, abfd) != amt) goto error_return; - som_swap_subspace_dictionary_in (&ext_subspace, &subspace); + som_swap_subspace_dictionary_in (&ext_subspace, &subspace); /* Setup the subspace name string. */ + if (subspace.name >= file_hdr->space_strings_size) + goto error_return; + subspace_name = subspace.name + space_strings; amt = strlen (subspace_name) + 1; @@ -2324,7 +2333,7 @@ setup_sections (bfd *abfd, else { /* The subspace_start field is not initialised in relocatable - only objects, so it cannot be used for length calculations. + only objects, so it cannot be used for length calculations. Instead we use the space_size value which we have been accumulating. This isn't an accurate estimate since it ignores alignment and ordering issues. */ @@ -2334,8 +2343,11 @@ setup_sections (bfd *abfd, } /* Now that we've read in all the subspace records, we need to assign a target index to each subspace. */ - amt = total_subspaces; - amt *= sizeof (asection *); + if (_bfd_mul_overflow (total_subspaces, sizeof (asection *), &amt)) + { + bfd_set_error (bfd_error_file_too_big); + goto error_return; + } subspace_sections = bfd_malloc (amt); if (subspace_sections == NULL) goto error_return; @@ -2356,27 +2368,20 @@ setup_sections (bfd *abfd, for (i = 0; i < total_subspaces; i++) subspace_sections[i]->target_index = i; - if (space_strings != NULL) - free (space_strings); - - if (subspace_sections != NULL) - free (subspace_sections); - - return TRUE; + free (space_strings); + free (subspace_sections); + return true; error_return: - if (space_strings != NULL) - free (space_strings); - - if (subspace_sections != NULL) - free (subspace_sections); - return FALSE; + free (space_strings); + free (subspace_sections); + return false; } /* Read in a SOM object and make it into a BFD. */ -static const bfd_target * +static bfd_cleanup som_object_p (bfd *abfd) { struct som_external_header ext_file_hdr; @@ -2385,7 +2390,7 @@ som_object_p (bfd *abfd) unsigned long current_offset = 0; struct som_external_lst_header ext_lst_header; struct som_external_som_entry ext_som_entry; - bfd_size_type amt; + size_t amt; unsigned int loc; #define ENTRY_SIZE sizeof (struct som_external_som_entry) @@ -2521,31 +2526,31 @@ som_object_p (bfd *abfd) /* Create a SOM object. */ -static bfd_boolean +static bool som_mkobject (bfd *abfd) { /* Allocate memory to hold backend information. */ abfd->tdata.som_data = bfd_zalloc (abfd, (bfd_size_type) sizeof (struct som_data_struct)); if (abfd->tdata.som_data == NULL) - return FALSE; - return TRUE; + return false; + return true; } /* Initialize some information in the file header. This routine makes not attempt at doing the right thing for a full executable; it is only meant to handle relocatable objects. */ -static bfd_boolean +static bool som_prep_headers (bfd *abfd) { struct som_header *file_hdr; asection *section; - bfd_size_type amt = sizeof (struct som_header); + size_t amt = sizeof (struct som_header); /* Make and attach a file header to the BFD. */ file_hdr = bfd_zalloc (abfd, amt); if (file_hdr == NULL) - return FALSE; + return false; obj_som_file_hdr (abfd) = file_hdr; if (abfd->flags & (EXEC_P | DYNAMIC)) @@ -2554,7 +2559,7 @@ som_prep_headers (bfd *abfd) amt = sizeof (struct som_exec_auxhdr); obj_som_exec_hdr (abfd) = bfd_zalloc (abfd, amt); if (obj_som_exec_hdr (abfd) == NULL) - return FALSE; + return false; if (abfd->flags & D_PAGED) file_hdr->a_magic = DEMAND_MAGIC; @@ -2596,7 +2601,7 @@ som_prep_headers (bfd *abfd) amt = sizeof (struct som_space_dictionary_record); som_section_data (section)->space_dict = bfd_zalloc (abfd, amt); if (som_section_data (section)->space_dict == NULL) - return FALSE; + return false; /* Set space attributes. Note most attributes of SOM spaces are set based on the subspaces it contains. */ som_section_data (section)->space_dict->loader_fix_index = -1; @@ -2618,7 +2623,7 @@ som_prep_headers (bfd *abfd) amt = sizeof (struct som_subspace_dictionary_record); som_section_data (section)->subspace_dict = bfd_zalloc (abfd, amt); if (som_section_data (section)->subspace_dict == NULL) - return FALSE; + return false; /* Set subspace attributes. Basic stuff is done here, additional attributes are filled in later as more information becomes @@ -2653,56 +2658,56 @@ som_prep_headers (bfd *abfd) som_section_data (section)->copy_data->dup_common; } } - return TRUE; + return true; } /* Return TRUE if the given section is a SOM space, FALSE otherwise. */ -static bfd_boolean +static bool som_is_space (asection *section) { /* If no copy data is available, then it's neither a space nor a subspace. */ if (som_section_data (section)->copy_data == NULL) - return FALSE; + return false; /* If the containing space isn't the same as the given section, then this isn't a space. */ if (som_section_data (section)->copy_data->container != section && (som_section_data (section)->copy_data->container->output_section != section)) - return FALSE; + return false; /* OK. Must be a space. */ - return TRUE; + return true; } /* Return TRUE if the given section is a SOM subspace, FALSE otherwise. */ -static bfd_boolean +static bool som_is_subspace (asection *section) { /* If no copy data is available, then it's neither a space nor a subspace. */ if (som_section_data (section)->copy_data == NULL) - return FALSE; + return false; /* If the containing space is the same as the given section, then this isn't a subspace. */ if (som_section_data (section)->copy_data->container == section || (som_section_data (section)->copy_data->container->output_section == section)) - return FALSE; + return false; /* OK. Must be a subspace. */ - return TRUE; + return true; } /* Return TRUE if the given space contains the given subspace. It is safe to assume space really is a space, and subspace really is a subspace. */ -static bfd_boolean +static bool som_is_container (asection *space, asection *subspace) { return (som_section_data (subspace)->copy_data->container == space) @@ -2790,13 +2795,16 @@ compare_subspaces (const void *arg1, const void *arg2) /* Perform various work in preparation for emitting the fixup stream. */ -static void +static bool som_prep_for_fixups (bfd *abfd, asymbol **syms, unsigned long num_syms) { unsigned long i; asection *section; asymbol **sorted_syms; - bfd_size_type amt; + size_t amt; + + if (num_syms == 0) + return true; /* Most SOM relocations involving a symbol have a length which is dependent on the index of the symbol. So symbols which are @@ -2868,9 +2876,14 @@ som_prep_for_fixups (bfd *abfd, asymbol **syms, unsigned long num_syms) /* Sort a copy of the symbol table, rather than the canonical output symbol table. */ - amt = num_syms; - amt *= sizeof (asymbol *); + if (_bfd_mul_overflow (num_syms, sizeof (asymbol *), &amt)) + { + bfd_set_error (bfd_error_no_memory); + return false; + } sorted_syms = bfd_zalloc (abfd, amt); + if (sorted_syms == NULL) + return false; memcpy (sorted_syms, syms, num_syms * sizeof (asymbol *)); qsort (sorted_syms, num_syms, sizeof (asymbol *), compare_syms); obj_som_sorted_syms (abfd) = sorted_syms; @@ -2886,9 +2899,10 @@ som_prep_for_fixups (bfd *abfd, asymbol **syms, unsigned long num_syms) else som_symbol_data (sorted_syms[i])->index = i; } + return true; } -static bfd_boolean +static bool som_write_fixups (bfd *abfd, unsigned long current_offset, unsigned int *total_reloc_sizep) @@ -2902,7 +2916,7 @@ som_write_fixups (bfd *abfd, unsigned int subspace_reloc_size = 0; unsigned int num_spaces = obj_som_file_hdr (abfd)->space_total; asection *section = abfd->sections; - bfd_size_type amt; + size_t amt; memset (tmp_space, 0, SOM_TMP_BUFSIZE); p = tmp_space; @@ -2957,7 +2971,7 @@ som_write_fixups (bfd *abfd, for this subspace in preparation for writing out its fixup stream. */ if (bfd_seek (abfd, current_offset + total_reloc_size, SEEK_SET) != 0) - return FALSE; + return false; /* Buffer space has already been allocated. Just perform some initialization here. */ @@ -2996,7 +3010,7 @@ som_write_fixups (bfd *abfd, { amt = p - tmp_space; if (bfd_bwrite ((void *) tmp_space, amt, abfd) != amt) - return FALSE; + return false; p = tmp_space; som_initialize_reloc_queue (reloc_queue); @@ -3281,7 +3295,7 @@ som_write_fixups (bfd *abfd, /* Scribble out the relocations. */ amt = p - tmp_space; if (bfd_bwrite ((void *) tmp_space, amt, abfd) != amt) - return FALSE; + return false; p = tmp_space; total_reloc_size += subspace_reloc_size; @@ -3291,12 +3305,12 @@ som_write_fixups (bfd *abfd, section = section->next; } *total_reloc_sizep = total_reloc_size; - return TRUE; + return true; } /* Write out the space/subspace string table. */ -static bfd_boolean +static bool som_write_space_strings (bfd *abfd, unsigned long current_offset, unsigned int *string_sizep) @@ -3304,17 +3318,20 @@ som_write_space_strings (bfd *abfd, /* Chunk of memory that we can use as buffer space, then throw away. */ size_t tmp_space_size = SOM_TMP_BUFSIZE; - char *tmp_space = xmalloc (tmp_space_size); + char *tmp_space = bfd_malloc (tmp_space_size); char *p = tmp_space; unsigned int strings_size = 0; asection *section; - bfd_size_type amt; + size_t amt; bfd_size_type res; + if (tmp_space == NULL) + return false; + /* Seek to the start of the space strings in preparation for writing them out. */ if (bfd_seek (abfd, (file_ptr) current_offset, SEEK_SET) != 0) - return FALSE; + return false; /* Walk through all the spaces and subspaces (order is not important) building up and writing string table entries for their names. */ @@ -3339,7 +3356,7 @@ som_write_space_strings (bfd *abfd, /* Flush buffer before refilling or reallocating. */ amt = p - tmp_space; if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt) - return FALSE; + return false; /* Reallocate if now empty buffer still too small. */ if (5 + length > tmp_space_size) @@ -3352,10 +3369,10 @@ som_write_space_strings (bfd *abfd, returning from this function.) The same technique is used a few more times below when a buffer is reallocated. */ - if (2 * tmp_space_size < length + 5) - tmp_space_size = length + 5; - else - tmp_space_size = 2 * tmp_space_size; + if (2 * tmp_space_size < length + 5) + tmp_space_size = length + 5; + else + tmp_space_size = 2 * tmp_space_size; tmp_space = xrealloc (tmp_space, tmp_space_size); } @@ -3395,14 +3412,14 @@ som_write_space_strings (bfd *abfd, res = bfd_bwrite ((void *) &tmp_space[0], amt, abfd); free (tmp_space); if (res != amt) - return FALSE; + return false; *string_sizep = strings_size; - return TRUE; + return true; } /* Write out the symbol string table. */ -static bfd_boolean +static bool som_write_symbol_strings (bfd *abfd, unsigned long current_offset, asymbol **syms, @@ -3414,12 +3431,15 @@ som_write_symbol_strings (bfd *abfd, /* Chunk of memory that we can use as buffer space, then throw away. */ size_t tmp_space_size = SOM_TMP_BUFSIZE; - char *tmp_space = xmalloc (tmp_space_size); + char *tmp_space = bfd_malloc (tmp_space_size); char *p = tmp_space; unsigned int strings_size = 0; - bfd_size_type amt; + size_t amt; bfd_size_type res; + if (tmp_space == NULL) + return false; + /* This gets a bit gruesome because of the compilation unit. The strings within the compilation unit are part of the symbol strings, but don't have symbol_dictionary entries. So, manually @@ -3430,14 +3450,14 @@ som_write_symbol_strings (bfd *abfd, /* Seek to the start of the space strings in preparation for writing them out. */ if (bfd_seek (abfd, (file_ptr) current_offset, SEEK_SET) != 0) - return FALSE; + return false; if (compilation_unit) { for (i = 0; i < 4; i++) { - struct som_name_pt *name; - size_t length; + struct som_name_pt *name; + size_t length; switch (i) { @@ -3453,8 +3473,8 @@ som_write_symbol_strings (bfd *abfd, case 3: name = &compilation_unit->version_id; break; - default: - abort (); + default: + abort (); } length = strlen (name->name); @@ -3467,16 +3487,16 @@ som_write_symbol_strings (bfd *abfd, /* Flush buffer before refilling or reallocating. */ amt = p - tmp_space; if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt) - return FALSE; + return false; /* Reallocate if now empty buffer still too small. */ if (5 + length > tmp_space_size) { /* See alloca above for discussion of new size. */ - if (2 * tmp_space_size < 5 + length) - tmp_space_size = 5 + length; - else - tmp_space_size = 2 * tmp_space_size; + if (2 * tmp_space_size < 5 + length) + tmp_space_size = 5 + length; + else + tmp_space_size = 2 * tmp_space_size; tmp_space = xrealloc (tmp_space, tmp_space_size); } @@ -3496,7 +3516,7 @@ som_write_symbol_strings (bfd *abfd, /* Next comes the string itself + a null terminator. */ strcpy (p, name->name); - name->strx = strings_size; + name->strx = strings_size; p += length + 1; strings_size += length + 1; @@ -3522,16 +3542,16 @@ som_write_symbol_strings (bfd *abfd, /* Flush buffer before refilling or reallocating. */ amt = p - tmp_space; if (bfd_bwrite ((void *) &tmp_space[0], amt, abfd) != amt) - return FALSE; + return false; /* Reallocate if now empty buffer still too small. */ if (5 + length > tmp_space_size) { /* See alloca above for discussion of new size. */ - if (2 * tmp_space_size < 5 + length) - tmp_space_size = 5 + length; - else - tmp_space_size = 2 * tmp_space_size; + if (2 * tmp_space_size < 5 + length) + tmp_space_size = 5 + length; + else + tmp_space_size = 2 * tmp_space_size; tmp_space = xrealloc (tmp_space, tmp_space_size); } @@ -3568,17 +3588,17 @@ som_write_symbol_strings (bfd *abfd, res = bfd_bwrite ((void *) &tmp_space[0], amt, abfd); free (tmp_space); if (res != amt) - return FALSE; + return false; *string_sizep = strings_size; - return TRUE; + return true; } /* Compute variable information to be placed in the SOM headers, space/subspace dictionaries, relocation streams, etc. Begin writing parts of the object file. */ -static bfd_boolean +static bool som_begin_writing (bfd *abfd) { unsigned long current_offset = 0; @@ -3624,16 +3644,16 @@ som_begin_writing (bfd *abfd) bfd_size_type len; if (bfd_seek (abfd, (file_ptr) current_offset, SEEK_SET) != 0) - return FALSE; + return false; /* Write the aux_id structure and the string length. */ len = sizeof (struct som_external_string_auxhdr); obj_som_file_hdr (abfd)->aux_header_size += len; current_offset += len; som_swap_string_auxhdr_out - (obj_som_version_hdr (abfd), &ext_string_auxhdr); + (obj_som_version_hdr (abfd), &ext_string_auxhdr); if (bfd_bwrite (&ext_string_auxhdr, len, abfd) != len) - return FALSE; + return false; /* Write the version string. */ len = obj_som_version_hdr (abfd)->header_id.length - 4; @@ -3641,7 +3661,7 @@ som_begin_writing (bfd *abfd) current_offset += len; if (bfd_bwrite ((void *) obj_som_version_hdr (abfd)->string, len, abfd) != len) - return FALSE; + return false; } if (obj_som_copyright_hdr (abfd) != NULL) @@ -3650,16 +3670,16 @@ som_begin_writing (bfd *abfd) bfd_size_type len; if (bfd_seek (abfd, (file_ptr) current_offset, SEEK_SET) != 0) - return FALSE; + return false; /* Write the aux_id structure and the string length. */ len = sizeof (struct som_external_string_auxhdr); obj_som_file_hdr (abfd)->aux_header_size += len; current_offset += len; som_swap_string_auxhdr_out - (obj_som_copyright_hdr (abfd), &ext_string_auxhdr); + (obj_som_copyright_hdr (abfd), &ext_string_auxhdr); if (bfd_bwrite (&ext_string_auxhdr, len, abfd) != len) - return FALSE; + return false; /* Write the copyright string. */ len = obj_som_copyright_hdr (abfd)->header_id.length - 4; @@ -3667,7 +3687,7 @@ som_begin_writing (bfd *abfd) current_offset += len; if (bfd_bwrite ((void *) obj_som_copyright_hdr (abfd)->string, len, abfd) != len) - return FALSE; + return false; } /* Next comes the initialization pointers; we have no initialization @@ -3717,7 +3737,7 @@ som_begin_writing (bfd *abfd) /* Scribble out the space strings. */ if (! som_write_space_strings (abfd, current_offset, &strings_size)) - return FALSE; + return false; /* Record total string table size in the header and update the current offset. */ @@ -3914,9 +3934,9 @@ som_begin_writing (bfd *abfd) if (abfd->flags & (EXEC_P | DYNAMIC)) current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE); if (bfd_seek (abfd, (file_ptr) current_offset - 1, SEEK_SET) != 0) - return FALSE; + return false; if (bfd_bwrite ((void *) "", (bfd_size_type) 1, abfd) != 1) - return FALSE; + return false; obj_som_file_hdr (abfd)->unloadable_sp_size = current_offset - obj_som_file_hdr (abfd)->unloadable_sp_location; @@ -3928,12 +3948,12 @@ som_begin_writing (bfd *abfd) /* Done. Store the total size of the SOM so far. */ obj_som_file_hdr (abfd)->som_length = current_offset; - return TRUE; + return true; } /* Finally, scribble out the various headers to the disk. */ -static bfd_boolean +static bool som_finish_writing (bfd *abfd) { int num_spaces = som_count_spaces (abfd); @@ -3944,7 +3964,7 @@ som_finish_writing (bfd *abfd) asection *section; unsigned long current_offset; unsigned int strings_size, total_reloc_size; - bfd_size_type amt; + size_t amt; struct som_external_header ext_header; /* We must set up the version identifier here as objcopy/strip copy @@ -3990,7 +4010,7 @@ som_finish_writing (bfd *abfd) if (! som_write_symbol_strings (abfd, current_offset, syms, num_syms, &strings_size, obj_som_compilation_unit (abfd))) - return FALSE; + return false; /* Record total string table size in header and update the current offset. */ @@ -3998,9 +4018,10 @@ som_finish_writing (bfd *abfd) current_offset += strings_size; /* Do prep work before handling fixups. */ - som_prep_for_fixups (abfd, - bfd_get_outsymbols (abfd), - bfd_get_symcount (abfd)); + if (!som_prep_for_fixups (abfd, + bfd_get_outsymbols (abfd), + bfd_get_symcount (abfd))) + return false; /* At the end of the file is the fixup stream which starts on a word boundary. */ @@ -4011,7 +4032,7 @@ som_finish_writing (bfd *abfd) /* Write the fixups and update fields in subspace headers which relate to the fixup stream. */ if (! som_write_fixups (abfd, current_offset, &total_reloc_size)) - return FALSE; + return false; /* Record the total size of the fixup stream in the file header. */ obj_som_file_hdr (abfd)->fixup_request_total = total_reloc_size; @@ -4022,7 +4043,7 @@ som_finish_writing (bfd *abfd) /* Now that the symbol table information is complete, build and write the symbol table. */ if (! som_build_and_write_symbol_table (abfd)) - return FALSE; + return false; /* Subspaces are written first so that we can set up information about them in their containing spaces as the subspace is written. */ @@ -4030,7 +4051,7 @@ som_finish_writing (bfd *abfd) /* Seek to the start of the subspace dictionary records. */ location = obj_som_file_hdr (abfd)->subspace_location; if (bfd_seek (abfd, location, SEEK_SET) != 0) - return FALSE; + return false; section = abfd->sections; /* Now for each loadable space write out records for its subspaces. */ @@ -4047,7 +4068,7 @@ som_finish_writing (bfd *abfd) subsection != NULL; subsection = subsection->next) { - struct som_external_subspace_dictionary_record ext_subspace_dict; + struct som_external_subspace_dictionary_record ext_subspace_dict; /* Skip any section which does not correspond to a space or subspace. Or does not have SEC_ALLOC set (and therefore @@ -4078,11 +4099,11 @@ som_finish_writing (bfd *abfd) som_section_data (subsection)->subspace_dict->space_index = i; /* Dump the current subspace header. */ - som_swap_subspace_dictionary_record_out - (som_section_data (subsection)->subspace_dict, &ext_subspace_dict); + som_swap_subspace_dictionary_record_out + (som_section_data (subsection)->subspace_dict, &ext_subspace_dict); amt = sizeof (struct som_subspace_dictionary_record); if (bfd_bwrite (&ext_subspace_dict, amt, abfd) != amt) - return FALSE; + return false; } /* Goto the next section. */ section = section->next; @@ -4104,7 +4125,7 @@ som_finish_writing (bfd *abfd) subsection != NULL; subsection = subsection->next) { - struct som_external_subspace_dictionary_record ext_subspace_dict; + struct som_external_subspace_dictionary_record ext_subspace_dict; /* Skip any section which does not correspond to a space or subspace, or which SEC_ALLOC set (and therefore handled @@ -4136,11 +4157,11 @@ som_finish_writing (bfd *abfd) som_section_data (subsection)->subspace_dict->space_index = i; /* Dump this subspace header. */ - som_swap_subspace_dictionary_record_out - (som_section_data (subsection)->subspace_dict, &ext_subspace_dict); + som_swap_subspace_dictionary_record_out + (som_section_data (subsection)->subspace_dict, &ext_subspace_dict); amt = sizeof (struct som_subspace_dictionary_record); if (bfd_bwrite (&ext_subspace_dict, amt, abfd) != amt) - return FALSE; + return false; } /* Goto the next section. */ section = section->next; @@ -4153,7 +4174,7 @@ som_finish_writing (bfd *abfd) dictionary records. */ location = obj_som_file_hdr (abfd)->space_location; if (bfd_seek (abfd, location, SEEK_SET) != 0) - return FALSE; + return false; section = abfd->sections; for (i = 0; i < num_spaces; i++) @@ -4166,10 +4187,10 @@ som_finish_writing (bfd *abfd) /* Dump its header. */ som_swap_space_dictionary_out (som_section_data (section)->space_dict, - &ext_space_dict); + &ext_space_dict); amt = sizeof (struct som_external_space_dictionary_record); if (bfd_bwrite (&ext_space_dict, amt, abfd) != amt) - return FALSE; + return false; /* Goto the next section. */ section = section->next; @@ -4182,14 +4203,14 @@ som_finish_writing (bfd *abfd) location = obj_som_file_hdr (abfd)->compiler_location; if (bfd_seek (abfd, location, SEEK_SET) != 0) - return FALSE; + return false; som_swap_compilation_unit_out - (obj_som_compilation_unit (abfd), &ext_comp_unit); + (obj_som_compilation_unit (abfd), &ext_comp_unit); amt = sizeof (struct som_external_compilation_unit); if (bfd_bwrite (&ext_comp_unit, amt, abfd) != amt) - return FALSE; + return false; } /* Setting of the system_id has to happen very late now that copying of @@ -4211,10 +4232,10 @@ som_finish_writing (bfd *abfd) /* Only thing left to do is write out the file header. It is always at location zero. Seek there and write it. */ if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0) - return FALSE; + return false; amt = sizeof (struct som_external_header); if (bfd_bwrite (&ext_header, amt, abfd) != amt) - return FALSE; + return false; /* Now write the exec header. */ if (abfd->flags & (EXEC_P | DYNAMIC)) @@ -4244,32 +4265,33 @@ som_finish_writing (bfd *abfd) || exec_header->exec_dfile + exec_header->exec_dsize > som_length) { bfd_set_error (bfd_error_bad_value); - return FALSE; + return false; } som_swap_exec_auxhdr_out (exec_header, &ext_exec_header); if (bfd_seek (abfd, obj_som_file_hdr (abfd)->aux_header_location, SEEK_SET) != 0) - return FALSE; + return false; amt = sizeof (ext_exec_header); if (bfd_bwrite (&ext_exec_header, amt, abfd) != amt) - return FALSE; + return false; } - return TRUE; + return true; } /* Compute and return the checksum for a SOM file header. */ -static unsigned long +static uint32_t som_compute_checksum (struct som_external_header *hdr) { - unsigned long checksum, count, i; - unsigned long *buffer = (unsigned long *) hdr; + size_t count, i; + uint32_t checksum; + uint32_t *buffer = (uint32_t *) hdr; checksum = 0; - count = sizeof (struct som_external_header) / 4; + count = sizeof (*hdr) / sizeof (*buffer); for (i = 0; i < count; i++) checksum ^= *(buffer + i); @@ -4390,9 +4412,9 @@ som_bfd_derive_misc_symbol_info (bfd *abfd ATTRIBUTE_UNUSED, /* The secondary_def field is for "weak" symbols. */ if (sym->flags & BSF_WEAK) - info->secondary_def = TRUE; + info->secondary_def = true; else - info->secondary_def = FALSE; + info->secondary_def = false; /* The is_comdat, is_common and dup_common fields provide various flavors of common. @@ -4436,7 +4458,7 @@ som_bfd_derive_misc_symbol_info (bfd *abfd ATTRIBUTE_UNUSED, /* Build and write, in one big chunk, the entire symbol table for this BFD. */ -static bfd_boolean +static bool som_build_and_write_symbol_table (bfd *abfd) { unsigned int num_syms = bfd_get_symcount (abfd); @@ -4445,13 +4467,19 @@ som_build_and_write_symbol_table (bfd *abfd) struct som_external_symbol_dictionary_record *som_symtab = NULL; unsigned int i; bfd_size_type symtab_size; + size_t amt; /* Compute total symbol table size and allocate a chunk of memory to hold the symbol table as we build it. */ - symtab_size = num_syms; - symtab_size *= sizeof (struct som_external_symbol_dictionary_record); - som_symtab = bfd_zmalloc (symtab_size); - if (som_symtab == NULL && symtab_size != 0) + if (_bfd_mul_overflow (num_syms, + sizeof (struct som_external_symbol_dictionary_record), + &amt)) + { + bfd_set_error (bfd_error_no_memory); + return false; + } + som_symtab = bfd_zmalloc (amt); + if (som_symtab == NULL && num_syms != 0) goto error_return; /* Walk over each symbol. */ @@ -4464,48 +4492,49 @@ som_build_and_write_symbol_table (bfd *abfd) By the time we get here, the index has already been computed and stored into the name field in the BFD symbol. */ bfd_putb32 (som_symbol_data (bfd_syms[i])->stringtab_offset, - som_symtab[i].name); + som_symtab[i].name); /* Derive SOM information from the BFD symbol. */ som_bfd_derive_misc_symbol_info (abfd, bfd_syms[i], &info); /* Now use it. */ flags = (info.symbol_type << SOM_SYMBOL_TYPE_SH) - | (info.symbol_scope << SOM_SYMBOL_SCOPE_SH) - | (info.arg_reloc << SOM_SYMBOL_ARG_RELOC_SH) - | (3 << SOM_SYMBOL_XLEAST_SH) - | (info.secondary_def ? SOM_SYMBOL_SECONDARY_DEF : 0) - | (info.is_common ? SOM_SYMBOL_IS_COMMON : 0) - | (info.dup_common ? SOM_SYMBOL_DUP_COMMON : 0); + | (info.symbol_scope << SOM_SYMBOL_SCOPE_SH) + | (info.arg_reloc << SOM_SYMBOL_ARG_RELOC_SH) + | (3 << SOM_SYMBOL_XLEAST_SH) + | (info.secondary_def ? SOM_SYMBOL_SECONDARY_DEF : 0) + | (info.is_common ? SOM_SYMBOL_IS_COMMON : 0) + | (info.dup_common ? SOM_SYMBOL_DUP_COMMON : 0); bfd_putb32 (flags, som_symtab[i].flags); flags = (info.symbol_info << SOM_SYMBOL_SYMBOL_INFO_SH) - | (info.is_comdat ? SOM_SYMBOL_IS_COMDAT : 0); + | (info.is_comdat ? SOM_SYMBOL_IS_COMDAT : 0); bfd_putb32 (flags, som_symtab[i].info); bfd_putb32 (info.symbol_value | info.priv_level, - som_symtab[i].symbol_value); + som_symtab[i].symbol_value); } /* Everything is ready, seek to the right location and scribble out the symbol table. */ if (bfd_seek (abfd, symtab_location, SEEK_SET) != 0) - return FALSE; + goto error_return; + symtab_size = num_syms; + symtab_size *= sizeof (struct som_external_symbol_dictionary_record); if (bfd_bwrite ((void *) som_symtab, symtab_size, abfd) != symtab_size) goto error_return; - if (som_symtab != NULL) - free (som_symtab); - return TRUE; + free (som_symtab); + return true; + error_return: - if (som_symtab != NULL) - free (som_symtab); - return FALSE; + free (som_symtab); + return false; } /* Write an object in SOM format. */ -static bfd_boolean +static bool som_write_object_contents (bfd *abfd) { if (! abfd->output_has_begun) @@ -4513,7 +4542,7 @@ som_write_object_contents (bfd *abfd) /* Set up fixed parts of the file, space, and subspace headers. Notify the world that output has begun. */ som_prep_headers (abfd); - abfd->output_has_begun = TRUE; + abfd->output_has_begun = true; /* Start writing the object file. This include all the string tables, fixup streams, and other portions of the object file. */ som_begin_writing (abfd); @@ -4524,7 +4553,7 @@ som_write_object_contents (bfd *abfd) /* Read and save the string table associated with the given BFD. */ -static bfd_boolean +static bool som_slurp_string_table (bfd *abfd) { char *stringtab; @@ -4532,7 +4561,7 @@ som_slurp_string_table (bfd *abfd) /* Use the saved version if its available. */ if (obj_som_stringtab (abfd) != NULL) - return TRUE; + return true; /* I don't think this can currently happen, and I'm not sure it should really be an error, but it's better than getting unpredictable results @@ -4540,24 +4569,22 @@ som_slurp_string_table (bfd *abfd) if (obj_som_stringtab_size (abfd) == 0) { bfd_set_error (bfd_error_no_symbols); - return FALSE; + return false; } /* Allocate and read in the string table. */ + if (bfd_seek (abfd, obj_som_str_filepos (abfd), SEEK_SET) != 0) + return false; amt = obj_som_stringtab_size (abfd); - stringtab = bfd_zmalloc (amt); + stringtab = (char *) _bfd_malloc_and_read (abfd, amt + 1, amt); if (stringtab == NULL) - return FALSE; - - if (bfd_seek (abfd, obj_som_str_filepos (abfd), SEEK_SET) != 0) - return FALSE; - - if (bfd_bread (stringtab, amt, abfd) != amt) - return FALSE; + return false; + /* Make sure that the strings are zero-terminated. */ + stringtab[amt] = 0; /* Save our results and return success. */ obj_som_stringtab (abfd) = stringtab; - return TRUE; + return true; } /* Return the amount of data (in bytes) required to hold the symbol @@ -4592,7 +4619,7 @@ bfd_section_from_som_symbol && symbol_type != ST_MILLICODE)) { int idx = (bfd_getb32 (symbol->info) >> SOM_SYMBOL_SYMBOL_INFO_SH) - & SOM_SYMBOL_SYMBOL_INFO_MASK; + & SOM_SYMBOL_SYMBOL_INFO_MASK; for (section = abfd->sections; section != NULL; section = section->next) if (section->target_index == idx && som_is_subspace (section)) @@ -4621,12 +4648,12 @@ bfd_section_from_som_symbol static unsigned int som_slurp_symbol_table (bfd *abfd) { - int symbol_count = bfd_get_symcount (abfd); - int symsize = sizeof (struct som_external_symbol_dictionary_record); + unsigned int symbol_count = bfd_get_symcount (abfd); + size_t symsize = sizeof (struct som_external_symbol_dictionary_record); char *stringtab; struct som_external_symbol_dictionary_record *buf = NULL, *bufp, *endbufp; - som_symbol_type *sym, *symbase; - bfd_size_type amt; + som_symbol_type *sym, *symbase = NULL; + size_t amt; /* Return saved value if it exists. */ if (obj_som_symtab (abfd) != NULL) @@ -4641,21 +4668,26 @@ som_slurp_symbol_table (bfd *abfd) stringtab = obj_som_stringtab (abfd); - amt = symbol_count; - amt *= sizeof (som_symbol_type); - symbase = bfd_zmalloc (amt); - if (symbase == NULL) - goto error_return; - /* Read in the external SOM representation. */ - amt = symbol_count; - amt *= symsize; - buf = bfd_malloc (amt); - if (buf == NULL && amt != 0) - goto error_return; + if (_bfd_mul_overflow (symbol_count, symsize, &amt)) + { + bfd_set_error (bfd_error_file_too_big); + goto error_return; + } if (bfd_seek (abfd, obj_som_sym_filepos (abfd), SEEK_SET) != 0) goto error_return; - if (bfd_bread (buf, amt, abfd) != amt) + buf = (struct som_external_symbol_dictionary_record *) + _bfd_malloc_and_read (abfd, amt, amt); + if (buf == NULL) + goto error_return; + + if (_bfd_mul_overflow (symbol_count, sizeof (som_symbol_type), &amt)) + { + bfd_set_error (bfd_error_file_too_big); + goto error_return; + } + symbase = bfd_zmalloc (amt); + if (symbase == NULL) goto error_return; /* Iterate over all the symbols and internalize them. */ @@ -4664,9 +4696,10 @@ som_slurp_symbol_table (bfd *abfd) { unsigned int flags = bfd_getb32 (bufp->flags); unsigned int symbol_type = - (flags >> SOM_SYMBOL_TYPE_SH) & SOM_SYMBOL_TYPE_MASK; + (flags >> SOM_SYMBOL_TYPE_SH) & SOM_SYMBOL_TYPE_MASK; unsigned int symbol_scope = - (flags >> SOM_SYMBOL_SCOPE_SH) & SOM_SYMBOL_SCOPE_MASK; + (flags >> SOM_SYMBOL_SCOPE_SH) & SOM_SYMBOL_SCOPE_MASK; + bfd_vma offset; /* I don't think we care about these. */ if (symbol_type == ST_SYM_EXT || symbol_type == ST_ARG_EXT) @@ -4694,13 +4727,20 @@ som_slurp_symbol_table (bfd *abfd) else som_symbol_data (sym)->som_type = SYMBOL_TYPE_UNKNOWN; som_symbol_data (sym)->tc_data.ap.hppa_arg_reloc = - (flags >> SOM_SYMBOL_ARG_RELOC_SH) & SOM_SYMBOL_ARG_RELOC_MASK; + (flags >> SOM_SYMBOL_ARG_RELOC_SH) & SOM_SYMBOL_ARG_RELOC_MASK; /* Some reasonable defaults. */ sym->symbol.the_bfd = abfd; - sym->symbol.name = bfd_getb32 (bufp->name) + stringtab; + offset = bfd_getb32 (bufp->name); + if (offset < obj_som_stringtab_size (abfd)) + sym->symbol.name = offset + stringtab; + else + { + bfd_set_error (bfd_error_bad_value); + goto error_return; + } sym->symbol.value = bfd_getb32 (bufp->symbol_value); - sym->symbol.section = 0; + sym->symbol.section = NULL; sym->symbol.flags = 0; switch (symbol_type) @@ -4760,26 +4800,28 @@ som_slurp_symbol_table (bfd *abfd) sym->symbol.section = bfd_section_from_som_symbol (abfd, bufp); sym->symbol.value -= sym->symbol.section->vma; break; + + default: + sym->symbol.section = bfd_und_section_ptr; + break; } /* Check for a weak symbol. */ if (flags & SOM_SYMBOL_SECONDARY_DEF) sym->symbol.flags |= BSF_WEAK; - /* Mark section symbols and symbols used by the debugger. Note $START$ is a magic code symbol, NOT a section symbol. */ if (sym->symbol.name[0] == '$' && sym->symbol.name[strlen (sym->symbol.name) - 1] == '$' && !strcmp (sym->symbol.name, sym->symbol.section->name)) sym->symbol.flags |= BSF_SECTION_SYM; - else if (CONST_STRNEQ (sym->symbol.name, "L$0\002")) + else if (startswith (sym->symbol.name, "L$0\002")) { sym->symbol.flags |= BSF_SECTION_SYM; sym->symbol.name = sym->symbol.section->name; } - else if (CONST_STRNEQ (sym->symbol.name, "L$0\001")) + else if (startswith (sym->symbol.name, "L$0\001")) sym->symbol.flags |= BSF_DEBUGGING; - /* Note increment at bottom of loop, since we skip some symbols we can not include it as part of the for statement. */ sym++; @@ -4787,19 +4829,18 @@ som_slurp_symbol_table (bfd *abfd) /* We modify the symbol count to record the number of BFD symbols we created. */ - bfd_get_symcount (abfd) = sym - symbase; + abfd->symcount = sym - symbase; /* Save our results and return success. */ obj_som_symtab (abfd) = symbase; successful_return: - if (buf != NULL) - free (buf); - return (TRUE); + free (buf); + return true; error_return: - if (buf != NULL) - free (buf); - return FALSE; + free (symbase); + free (buf); + return false; } /* Canonicalize a SOM symbol table. Return the number of entries @@ -4830,7 +4871,7 @@ som_canonicalize_symtab (bfd *abfd, asymbol **location) static asymbol * som_make_empty_symbol (bfd *abfd) { - bfd_size_type amt = sizeof (som_symbol_type); + size_t amt = sizeof (som_symbol_type); som_symbol_type *new_symbol_type = bfd_zalloc (abfd, amt); if (new_symbol_type == NULL) @@ -4872,7 +4913,7 @@ som_print_symbol (bfd *abfd, } } -static bfd_boolean +static bool som_bfd_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED, const char *name) { @@ -4898,7 +4939,7 @@ som_set_reloc_info (unsigned char *fixup, arelent *internal_relocs, asection *section, asymbol **symbols, - bfd_boolean just_count) + bool just_count) { unsigned int op, varname, deallocate_contents = 0; unsigned char *end_fixups = &fixup[end]; @@ -5007,7 +5048,7 @@ som_set_reloc_info (unsigned char *fixup, push (v); } else - /* An operator. Pop two two values from the stack and + /* An operator. Pop two values from the stack and use them as operands to the given operation. Push the result of the operation back on the stack. */ switch (c) @@ -5193,8 +5234,7 @@ som_set_reloc_info (unsigned char *fixup, if (!bfd_malloc_and_get_section (section->owner, section, &contents)) { - if (contents != NULL) - free (contents); + free (contents); return (unsigned) -1; } section->contents = contents; @@ -5234,69 +5274,68 @@ som_set_reloc_info (unsigned char *fixup, set to TRUE to indicate it only needs a count of the number of actual relocations. */ -static bfd_boolean +static bool som_slurp_reloc_table (bfd *abfd, asection *section, asymbol **symbols, - bfd_boolean just_count) + bool just_count) { unsigned char *external_relocs; unsigned int fixup_stream_size; arelent *internal_relocs; unsigned int num_relocs; - bfd_size_type amt; + size_t amt; fixup_stream_size = som_section_data (section)->reloc_size; /* If there were no relocations, then there is nothing to do. */ if (section->reloc_count == 0) - return TRUE; + return true; /* If reloc_count is -1, then the relocation stream has not been parsed. We must do so now to know how many relocations exist. */ if (section->reloc_count == (unsigned) -1) { + /* Read in the external forms. */ + if (bfd_seek (abfd, obj_som_reloc_filepos (abfd) + section->rel_filepos, + SEEK_SET) != 0) + return false; amt = fixup_stream_size; - external_relocs = bfd_malloc (amt); + external_relocs = _bfd_malloc_and_read (abfd, amt, amt); if (external_relocs == NULL) - return FALSE; - /* Read in the external forms. */ - if (bfd_seek (abfd, - obj_som_reloc_filepos (abfd) + section->rel_filepos, - SEEK_SET) - != 0) - return FALSE; - if (bfd_bread (external_relocs, amt, abfd) != amt) - return FALSE; + return false; /* Let callers know how many relocations found. also save the relocation stream as we will need it again. */ section->reloc_count = som_set_reloc_info (external_relocs, fixup_stream_size, - NULL, NULL, NULL, TRUE); + NULL, NULL, NULL, true); som_section_data (section)->reloc_stream = external_relocs; } /* If the caller only wanted a count, then return now. */ if (just_count) - return TRUE; + return true; num_relocs = section->reloc_count; external_relocs = som_section_data (section)->reloc_stream; /* Return saved information about the relocations if it is available. */ if (section->relocation != NULL) - return TRUE; + return true; - amt = num_relocs; - amt *= sizeof (arelent); - internal_relocs = bfd_zalloc (abfd, (amt)); + if (_bfd_mul_overflow (num_relocs, sizeof (arelent), &amt)) + { + bfd_set_error (bfd_error_file_too_big); + return false; + } + internal_relocs = bfd_zalloc (abfd, amt); if (internal_relocs == NULL) - return FALSE; + return false; /* Process and internalize the relocations. */ som_set_reloc_info (external_relocs, fixup_stream_size, - internal_relocs, section, symbols, FALSE); + internal_relocs, section, symbols, false); /* We're done with the external relocations. Free them. */ free (external_relocs); @@ -5304,7 +5343,7 @@ som_slurp_reloc_table (bfd *abfd, /* Save our results and return success. */ section->relocation = internal_relocs; - return TRUE; + return true; } /* Return the number of bytes required to store the relocation @@ -5317,7 +5356,7 @@ som_get_reloc_upper_bound (bfd *abfd, sec_ptr asect) and parse it to determine how many relocations exist. */ if (asect->flags & SEC_RELOC) { - if (! som_slurp_reloc_table (abfd, asect, NULL, TRUE)) + if (! som_slurp_reloc_table (abfd, asect, NULL, true)) return -1; return (asect->reloc_count + 1) * sizeof (arelent *); } @@ -5340,7 +5379,7 @@ som_canonicalize_reloc (bfd *abfd, arelent *tblptr; int count; - if (! som_slurp_reloc_table (abfd, section, symbols, FALSE)) + if (! som_slurp_reloc_table (abfd, section, symbols, false)) return -1; count = section->reloc_count; @@ -5357,16 +5396,16 @@ extern const bfd_target hppa_som_vec; /* A hook to set up object file dependent section information. */ -static bfd_boolean +static bool som_new_section_hook (bfd *abfd, asection *newsect) { if (!newsect->used_by_bfd) { - bfd_size_type amt = sizeof (struct som_section_data_struct); + size_t amt = sizeof (struct som_section_data_struct); newsect->used_by_bfd = bfd_zalloc (abfd, amt); if (!newsect->used_by_bfd) - return FALSE; + return false; } newsect->alignment_power = 3; @@ -5377,7 +5416,7 @@ som_new_section_hook (bfd *abfd, asection *newsect) /* Copy any private info we understand from the input symbol to the output symbol. */ -static bfd_boolean +static bool som_bfd_copy_private_symbol_data (bfd *ibfd, asymbol *isymbol, bfd *obfd, @@ -5389,37 +5428,37 @@ som_bfd_copy_private_symbol_data (bfd *ibfd, /* One day we may try to grok other private data. */ if (ibfd->xvec->flavour != bfd_target_som_flavour || obfd->xvec->flavour != bfd_target_som_flavour) - return FALSE; + return false; /* The only private information we need to copy is the argument relocation bits. */ output_symbol->tc_data.ap.hppa_arg_reloc = input_symbol->tc_data.ap.hppa_arg_reloc; - return TRUE; + return true; } /* Copy any private info we understand from the input section to the output section. */ -static bfd_boolean +static bool som_bfd_copy_private_section_data (bfd *ibfd, asection *isection, bfd *obfd, asection *osection) { - bfd_size_type amt; + size_t amt; /* One day we may try to grok other private data. */ if (ibfd->xvec->flavour != bfd_target_som_flavour || obfd->xvec->flavour != bfd_target_som_flavour || (!som_is_space (isection) && !som_is_subspace (isection))) - return TRUE; + return true; amt = sizeof (struct som_copyable_section_data_struct); som_section_data (osection)->copy_data = bfd_zalloc (obfd, amt); if (som_section_data (osection)->copy_data == NULL) - return FALSE; + return false; memcpy (som_section_data (osection)->copy_data, som_section_data (isection)->copy_data, @@ -5427,38 +5466,48 @@ som_bfd_copy_private_section_data (bfd *ibfd, /* Reparent if necessary. */ if (som_section_data (osection)->copy_data->container) - som_section_data (osection)->copy_data->container = - som_section_data (osection)->copy_data->container->output_section; + { + if (som_section_data (osection)->copy_data->container->output_section) + som_section_data (osection)->copy_data->container = + som_section_data (osection)->copy_data->container->output_section; + else + { + /* User has specified a subspace without its containing space. */ + _bfd_error_handler (_("%pB[%pA]: no output section for space %pA"), + obfd, osection, som_section_data (osection)->copy_data->container); + return false; + } + } - return TRUE; + return true; } /* Copy any private info we understand from the input bfd to the output bfd. */ -static bfd_boolean +static bool som_bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd) { /* One day we may try to grok other private data. */ if (ibfd->xvec->flavour != bfd_target_som_flavour || obfd->xvec->flavour != bfd_target_som_flavour) - return TRUE; + return true; /* Allocate some memory to hold the data we need. */ obj_som_exec_data (obfd) = bfd_zalloc (obfd, (bfd_size_type) sizeof (struct som_exec_data)); if (obj_som_exec_data (obfd) == NULL) - return FALSE; + return false; /* Now copy the data. */ memcpy (obj_som_exec_data (obfd), obj_som_exec_data (ibfd), sizeof (struct som_exec_data)); - return TRUE; + return true; } /* Display the SOM header. */ -static bfd_boolean +static bool som_bfd_print_private_bfd_data (bfd *abfd, void *farg) { struct som_exec_auxhdr *exec_header; @@ -5486,7 +5535,7 @@ som_bfd_print_private_bfd_data (bfd *abfd, void *farg) fprintf (f, " length %#x\n", auxhdr->length); /* Note that, depending on the HP-UX version, the following fields can be - either ints, or longs. */ + either ints, or longs. */ fprintf (f, " text size %#lx\n", (long) exec_header->exec_tsize); fprintf (f, " text memory offset %#lx\n", (long) exec_header->exec_tmem); @@ -5500,13 +5549,13 @@ som_bfd_print_private_bfd_data (bfd *abfd, void *farg) fprintf (f, " bss initializer %#lx\n", (long) exec_header->exec_bfill); } - return TRUE; + return true; } /* Set backend info for sections which can not be described in the BFD data structures. */ -bfd_boolean +bool bfd_som_set_section_attributes (asection *section, int defined, int private, @@ -5516,24 +5565,24 @@ bfd_som_set_section_attributes (asection *section, /* Allocate memory to hold the magic information. */ if (som_section_data (section)->copy_data == NULL) { - bfd_size_type amt = sizeof (struct som_copyable_section_data_struct); + size_t amt = sizeof (struct som_copyable_section_data_struct); som_section_data (section)->copy_data = bfd_zalloc (section->owner, amt); if (som_section_data (section)->copy_data == NULL) - return FALSE; + return false; } som_section_data (section)->copy_data->sort_key = sort_key; som_section_data (section)->copy_data->is_defined = defined; som_section_data (section)->copy_data->is_private = private; som_section_data (section)->copy_data->container = section; som_section_data (section)->copy_data->space_number = spnum; - return TRUE; + return true; } /* Set backend info for subsections which can not be described in the BFD data structures. */ -bfd_boolean +bool bfd_som_set_subsection_attributes (asection *section, asection *container, int access_ctr, @@ -5546,11 +5595,11 @@ bfd_som_set_subsection_attributes (asection *section, /* Allocate memory to hold the magic information. */ if (som_section_data (section)->copy_data == NULL) { - bfd_size_type amt = sizeof (struct som_copyable_section_data_struct); + size_t amt = sizeof (struct som_copyable_section_data_struct); som_section_data (section)->copy_data = bfd_zalloc (section->owner, amt); if (som_section_data (section)->copy_data == NULL) - return FALSE; + return false; } som_section_data (section)->copy_data->sort_key = sort_key; som_section_data (section)->copy_data->access_control_bits = access_ctr; @@ -5559,7 +5608,7 @@ bfd_som_set_subsection_attributes (asection *section, som_section_data (section)->copy_data->is_comdat = comdat; som_section_data (section)->copy_data->is_common = common; som_section_data (section)->copy_data->dup_common = dup_common; - return TRUE; + return true; } /* Set the full SOM symbol type. SOM needs far more symbol information @@ -5577,10 +5626,10 @@ bfd_som_set_symbol_type (asymbol *symbol, unsigned int type) /* Attach an auxiliary header to the BFD backend so that it may be written into the object file. */ -bfd_boolean +bool bfd_som_attach_aux_hdr (bfd *abfd, int type, char *string) { - bfd_size_type amt; + size_t amt; if (type == VERSION_AUX_ID) { @@ -5592,7 +5641,7 @@ bfd_som_attach_aux_hdr (bfd *abfd, int type, char *string) amt = sizeof (struct som_string_auxhdr) + len + pad; obj_som_version_hdr (abfd) = bfd_zalloc (abfd, amt); if (!obj_som_version_hdr (abfd)) - return FALSE; + return false; obj_som_version_hdr (abfd)->header_id.type = VERSION_AUX_ID; obj_som_version_hdr (abfd)->header_id.length = 4 + len + pad; obj_som_version_hdr (abfd)->string_length = len; @@ -5601,7 +5650,7 @@ bfd_som_attach_aux_hdr (bfd *abfd, int type, char *string) } else if (type == COPYRIGHT_AUX_ID) { - int len = strlen (string); + size_t len = strlen (string); int pad = 0; if (len % 4) @@ -5609,20 +5658,20 @@ bfd_som_attach_aux_hdr (bfd *abfd, int type, char *string) amt = sizeof (struct som_string_auxhdr) + len + pad; obj_som_copyright_hdr (abfd) = bfd_zalloc (abfd, amt); if (!obj_som_copyright_hdr (abfd)) - return FALSE; + return false; obj_som_copyright_hdr (abfd)->header_id.type = COPYRIGHT_AUX_ID; obj_som_copyright_hdr (abfd)->header_id.length = len + pad + 4; obj_som_copyright_hdr (abfd)->string_length = len; memcpy (obj_som_copyright_hdr (abfd)->string, string, len); memset (obj_som_copyright_hdr (abfd)->string + len, 0, pad); } - return TRUE; + return true; } /* Attach a compilation unit header to the BFD backend so that it may be written into the object file. */ -bfd_boolean +bool bfd_som_attach_compilation_unit (bfd *abfd, const char *name, const char *language_name, @@ -5634,14 +5683,14 @@ bfd_som_attach_compilation_unit (bfd *abfd, n = (struct som_compilation_unit *) bfd_zalloc (abfd, (bfd_size_type) sizeof (*n)); if (n == NULL) - return FALSE; + return false; #define STRDUP(f) \ if (f != NULL) \ { \ n->f.name = bfd_alloc (abfd, (bfd_size_type) strlen (f) + 1); \ if (n->f.name == NULL) \ - return FALSE; \ + return false; \ strcpy (n->f.name, f); \ } @@ -5654,10 +5703,10 @@ bfd_som_attach_compilation_unit (bfd *abfd, obj_som_compilation_unit (abfd) = n; - return TRUE; + return true; } -static bfd_boolean +static bool som_get_section_contents (bfd *abfd, sec_ptr section, void *location, @@ -5665,15 +5714,15 @@ som_get_section_contents (bfd *abfd, bfd_size_type count) { if (count == 0 || ((section->flags & SEC_HAS_CONTENTS) == 0)) - return TRUE; + return true; if ((bfd_size_type) (offset+count) > section->size || bfd_seek (abfd, (file_ptr) (section->filepos + offset), SEEK_SET) != 0 || bfd_bread (location, count, abfd) != count) - return FALSE; /* On error. */ - return TRUE; + return false; /* On error. */ + return true; } -static bfd_boolean +static bool som_set_section_contents (bfd *abfd, sec_ptr section, const void *location, @@ -5685,7 +5734,7 @@ som_set_section_contents (bfd *abfd, /* Set up fixed parts of the file, space, and subspace headers. Notify the world that output has begun. */ som_prep_headers (abfd); - abfd->output_has_begun = TRUE; + abfd->output_has_begun = true; /* Start writing the object file. This include all the string tables, fixup streams, and other portions of the object file. */ som_begin_writing (abfd); @@ -5695,20 +5744,20 @@ som_set_section_contents (bfd *abfd, are not generated at run time by the OS). */ if (!som_is_subspace (section) || ((section->flags & SEC_HAS_CONTENTS) == 0)) - return TRUE; + return true; /* Seek to the proper offset within the object file and write the data. */ offset += som_section_data (section)->subspace_dict->file_loc_init_value; if (bfd_seek (abfd, offset, SEEK_SET) != 0) - return FALSE; + return false; if (bfd_bwrite (location, count, abfd) != count) - return FALSE; - return TRUE; + return false; + return true; } -static bfd_boolean +static bool som_set_arch_mach (bfd *abfd, enum bfd_architecture arch, unsigned long machine) @@ -5717,7 +5766,7 @@ som_set_arch_mach (bfd *abfd, return bfd_default_set_arch_mach (abfd, arch, machine); } -static bfd_boolean +static bool som_find_nearest_line (bfd *abfd, asymbol **symbols, asection *section, @@ -5727,7 +5776,7 @@ som_find_nearest_line (bfd *abfd, unsigned int *line_ptr, unsigned int *discriminator_ptr) { - bfd_boolean found; + bool found; asymbol *func; bfd_vma low_func; asymbol **p; @@ -5736,16 +5785,16 @@ som_find_nearest_line (bfd *abfd, *discriminator_ptr = 0; if (! _bfd_stab_section_find_nearest_line (abfd, symbols, section, offset, - & found, filename_ptr, - functionname_ptr, line_ptr, - & somdata (abfd).line_info)) - return FALSE; + & found, filename_ptr, + functionname_ptr, line_ptr, + & somdata (abfd).line_info)) + return false; if (found) - return TRUE; + return true; if (symbols == NULL) - return FALSE; + return false; /* Fallback: find function name from symbols table. */ func = NULL; @@ -5766,13 +5815,13 @@ som_find_nearest_line (bfd *abfd, } if (func == NULL) - return FALSE; + return false; *filename_ptr = NULL; *functionname_ptr = bfd_asymbol_name (func); *line_ptr = 0; - return TRUE; + return true; } static int @@ -5803,6 +5852,11 @@ som_decode_symclass (asymbol *symbol) { char c; + /* If the symbol did not have a scope specified, + then it will not have associated section. */ + if (symbol == NULL || symbol->section == NULL) + return '?'; + if (bfd_is_com_section (symbol->section)) return 'C'; if (bfd_is_und_section (symbol->section)) @@ -5864,31 +5918,32 @@ som_get_symbol_info (bfd *ignore_abfd ATTRIBUTE_UNUSED, /* Count the number of symbols in the archive symbol table. Necessary so that we can allocate space for all the carsyms at once. */ -static bfd_boolean +static bool som_bfd_count_ar_symbols (bfd *abfd, struct som_lst_header *lst_header, symindex *count) { unsigned int i; unsigned char *hash_table; - bfd_size_type amt; + size_t amt; file_ptr lst_filepos; lst_filepos = bfd_tell (abfd) - sizeof (struct som_external_lst_header); - amt = lst_header->hash_size * 4; - hash_table = bfd_malloc (amt); - if (hash_table == NULL && amt != 0) + /* Read in the hash table. The hash table is an array of 32-bit + file offsets which point to the hash chains. */ + if (_bfd_mul_overflow (lst_header->hash_size, 4, &amt)) + { + bfd_set_error (bfd_error_file_too_big); + return false; + } + hash_table = _bfd_malloc_and_read (abfd, amt, amt); + if (hash_table == NULL && lst_header->hash_size != 0) goto error_return; /* Don't forget to initialize the counter! */ *count = 0; - /* Read in the hash table. The has table is an array of 32bit file offsets - which point to the hash chains. */ - if (bfd_bread ((void *) hash_table, amt, abfd) != amt) - goto error_return; - /* Walk each chain counting the number of symbols found on that particular chain. */ for (i = 0; i < lst_header->hash_size; i++) @@ -5914,10 +5969,19 @@ som_bfd_count_ar_symbols (bfd *abfd, /* Now iterate through the rest of the symbols on this chain. */ while (1) { - unsigned int next_entry = bfd_getb32 (ext_lst_symbol.next_entry); + unsigned int next_entry = bfd_getb32 (ext_lst_symbol.next_entry); - if (next_entry == 0) - break; + if (next_entry == 0) + break; + + /* Assume symbols on a chain are in increasing file offset + order. Otherwise we can loop here with fuzzed input. */ + if (next_entry < hash_val + sizeof (ext_lst_symbol)) + { + bfd_set_error (bfd_error_bad_value); + goto error_return; + } + hash_val = next_entry; /* Seek to the next symbol. */ if (bfd_seek (abfd, lst_filepos + next_entry, SEEK_SET) != 0) @@ -5931,20 +5995,18 @@ som_bfd_count_ar_symbols (bfd *abfd, (*count)++; } } - if (hash_table != NULL) - free (hash_table); - return TRUE; + free (hash_table); + return true; error_return: - if (hash_table != NULL) - free (hash_table); - return FALSE; + free (hash_table); + return false; } /* Fill in the canonical archive symbols (SYMS) from the archive described by ABFD and LST_HEADER. */ -static bfd_boolean +static bool som_bfd_fill_in_ar_symbols (bfd *abfd, struct som_lst_header *lst_header, carsym **syms) @@ -5953,19 +6015,21 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, carsym *set = syms[0]; unsigned char *hash_table; struct som_external_som_entry *som_dict = NULL; - bfd_size_type amt; + size_t amt; file_ptr lst_filepos; unsigned int string_loc; lst_filepos = bfd_tell (abfd) - sizeof (struct som_external_lst_header); - amt = lst_header->hash_size * 4; - hash_table = bfd_malloc (amt); - if (hash_table == NULL && amt != 0) - goto error_return; /* Read in the hash table. The has table is an array of 32bit file offsets which point to the hash chains. */ - if (bfd_bread ((void *) hash_table, amt, abfd) != amt) + if (_bfd_mul_overflow (lst_header->hash_size, 4, &amt)) + { + bfd_set_error (bfd_error_file_too_big); + return false; + } + hash_table = _bfd_malloc_and_read (abfd, amt, amt); + if (hash_table == NULL && lst_header->hash_size != 0) goto error_return; /* Seek to and read in the SOM dictionary. We will need this to fill @@ -5973,12 +6037,15 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, if (bfd_seek (abfd, lst_filepos + lst_header->dir_loc, SEEK_SET) != 0) goto error_return; - amt = lst_header->module_count * sizeof (struct som_external_som_entry); - som_dict = bfd_malloc (amt); - if (som_dict == NULL && amt != 0) - goto error_return; - - if (bfd_bread ((void *) som_dict, amt, abfd) != amt) + if (_bfd_mul_overflow (lst_header->module_count, + sizeof (struct som_external_som_entry), &amt)) + { + bfd_set_error (bfd_error_file_too_big); + goto error_return; + } + som_dict = (struct som_external_som_entry *) + _bfd_malloc_and_read (abfd, amt, amt); + if (som_dict == NULL && lst_header->module_count != 0) goto error_return; string_loc = lst_header->string_loc; @@ -5988,8 +6055,10 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, { struct som_external_lst_symbol_record lst_symbol; unsigned int hash_val; - unsigned int len; + size_t len; unsigned char ext_len[4]; + char *name; + unsigned int ndx; /* An empty chain has zero as it's file offset. */ hash_val = bfd_getb32 (hash_table + 4 * i); @@ -6012,7 +6081,7 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, index can point *anywhere* in the archive to save space, so just using the string table would not be safe. */ if (bfd_seek (abfd, (lst_filepos + string_loc - + bfd_getb32 (lst_symbol.name) - 4), SEEK_SET) != 0) + + bfd_getb32 (lst_symbol.name) - 4), SEEK_SET) != 0) goto error_return; if (bfd_bread (&ext_len, (bfd_size_type) 4, abfd) != 4) @@ -6020,19 +6089,27 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, len = bfd_getb32 (ext_len); /* Allocate space for the name and null terminate it too. */ - set->name = bfd_zalloc (abfd, (bfd_size_type) len + 1); - if (!set->name) - goto error_return; - if (bfd_bread (set->name, (bfd_size_type) len, abfd) != len) + if (len == (size_t) -1) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } + name = (char *) _bfd_alloc_and_read (abfd, len + 1, len); + if (!name) goto error_return; - - set->name[len] = 0; + name[len] = 0; + set->name = name; /* Fill in the file offset. Note that the "location" field points to the SOM itself, not the ar_hdr in front of it. */ - set->file_offset = - bfd_getb32 (som_dict[bfd_getb32 (lst_symbol.som_index)].location) - - sizeof (struct ar_hdr); + ndx = bfd_getb32 (lst_symbol.som_index); + if (ndx >= lst_header->module_count) + { + bfd_set_error (bfd_error_bad_value); + goto error_return; + } + set->file_offset + = bfd_getb32 (som_dict[ndx].location) - sizeof (struct ar_hdr); /* Go to the next symbol. */ set++; @@ -6040,10 +6117,10 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, /* Iterate through the rest of the chain. */ while (1) { - unsigned int next_entry = bfd_getb32 (lst_symbol.next_entry); + unsigned int next_entry = bfd_getb32 (lst_symbol.next_entry); - if (next_entry == 0) - break; + if (next_entry == 0) + break; /* Seek to the next symbol and read it in. */ if (bfd_seek (abfd, lst_filepos + next_entry, SEEK_SET) != 0) @@ -6055,27 +6132,35 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, /* Seek to the name length & string and read them in. */ if (bfd_seek (abfd, lst_filepos + string_loc - + bfd_getb32 (lst_symbol.name) - 4, SEEK_SET) != 0) + + bfd_getb32 (lst_symbol.name) - 4, SEEK_SET) != 0) goto error_return; if (bfd_bread (&ext_len, (bfd_size_type) 4, abfd) != 4) goto error_return; - len = bfd_getb32 (ext_len); + len = bfd_getb32 (ext_len); /* Allocate space for the name and null terminate it too. */ - set->name = bfd_zalloc (abfd, (bfd_size_type) len + 1); - if (!set->name) - goto error_return; - - if (bfd_bread (set->name, (bfd_size_type) len, abfd) != len) + if (len == (size_t) -1) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } + name = (char *) _bfd_alloc_and_read (abfd, len + 1, len); + if (!name) goto error_return; - set->name[len] = 0; + name[len] = 0; + set->name = name; /* Fill in the file offset. Note that the "location" field points to the SOM itself, not the ar_hdr in front of it. */ - set->file_offset = - bfd_getb32 (som_dict[bfd_getb32 (lst_symbol.som_index)].location) - - sizeof (struct ar_hdr); + ndx = bfd_getb32 (lst_symbol.som_index); + if (ndx >= lst_header->module_count) + { + bfd_set_error (bfd_error_bad_value); + goto error_return; + } + set->file_offset + = bfd_getb32 (som_dict[ndx].location) - sizeof (struct ar_hdr); /* Go on to the next symbol. */ set++; @@ -6083,23 +6168,19 @@ som_bfd_fill_in_ar_symbols (bfd *abfd, } /* If we haven't died by now, then we successfully read the entire archive symbol table. */ - if (hash_table != NULL) - free (hash_table); - if (som_dict != NULL) - free (som_dict); - return TRUE; + free (hash_table); + free (som_dict); + return true; error_return: - if (hash_table != NULL) - free (hash_table); - if (som_dict != NULL) - free (som_dict); - return FALSE; + free (hash_table); + free (som_dict); + return false; } /* Read in the LST from the archive. */ -static bfd_boolean +static bool som_slurp_armap (bfd *abfd) { struct som_external_lst_header ext_lst_header; @@ -6108,34 +6189,34 @@ som_slurp_armap (bfd *abfd) unsigned int parsed_size; struct artdata *ardata = bfd_ardata (abfd); char nextname[17]; - bfd_size_type amt = 16; + size_t amt = 16; int i = bfd_bread ((void *) nextname, amt, abfd); /* Special cases. */ if (i == 0) - return TRUE; + return true; if (i != 16) - return FALSE; + return false; if (bfd_seek (abfd, (file_ptr) -16, SEEK_CUR) != 0) - return FALSE; + return false; /* For archives without .o files there is no symbol table. */ - if (! CONST_STRNEQ (nextname, "/ ")) + if (! startswith (nextname, "/ ")) { - bfd_has_map (abfd) = FALSE; - return TRUE; + abfd->has_armap = false; + return true; } /* Read in and sanity check the archive header. */ amt = sizeof (struct ar_hdr); if (bfd_bread ((void *) &ar_header, amt, abfd) != amt) - return FALSE; + return false; if (strncmp (ar_header.ar_fmag, ARFMAG, 2)) { bfd_set_error (bfd_error_malformed_archive); - return FALSE; + return false; } /* How big is the archive symbol table entry? */ @@ -6144,7 +6225,7 @@ som_slurp_armap (bfd *abfd) if (errno != 0) { bfd_set_error (bfd_error_malformed_archive); - return FALSE; + return false; } /* Save off the file offset of the first real user data. */ @@ -6154,7 +6235,7 @@ som_slurp_armap (bfd *abfd) in just a minute. */ amt = sizeof (struct som_external_lst_header); if (bfd_bread ((void *) &ext_lst_header, amt, abfd) != amt) - return FALSE; + return false; som_swap_lst_header_in (&ext_lst_header, &lst_header); @@ -6162,39 +6243,42 @@ som_slurp_armap (bfd *abfd) if (lst_header.a_magic != LIBMAGIC) { bfd_set_error (bfd_error_malformed_archive); - return FALSE; + return false; } /* Count the number of symbols in the library symbol table. */ if (! som_bfd_count_ar_symbols (abfd, &lst_header, &ardata->symdef_count)) - return FALSE; + return false; /* Get back to the start of the library symbol table. */ if (bfd_seek (abfd, (ardata->first_file_filepos - parsed_size + sizeof (struct som_external_lst_header)), - SEEK_SET) != 0) - return FALSE; + SEEK_SET) != 0) + return false; /* Initialize the cache and allocate space for the library symbols. */ ardata->cache = 0; - amt = ardata->symdef_count; - amt *= sizeof (carsym); + if (_bfd_mul_overflow (ardata->symdef_count, sizeof (carsym), &amt)) + { + bfd_set_error (bfd_error_file_too_big); + return false; + } ardata->symdefs = bfd_alloc (abfd, amt); if (!ardata->symdefs) - return FALSE; + return false; /* Now fill in the canonical archive symbols. */ if (! som_bfd_fill_in_ar_symbols (abfd, &lst_header, &ardata->symdefs)) - return FALSE; + return false; /* Seek back to the "first" file in the archive. Note the "first" file may be the extended name table. */ if (bfd_seek (abfd, ardata->first_file_filepos, SEEK_SET) != 0) - return FALSE; + return false; /* Notify the generic archive code that we have a symbol map. */ - bfd_has_map (abfd) = TRUE; - return TRUE; + abfd->has_armap = true; + return true; } /* Begin preparing to write a SOM library symbol table. @@ -6202,7 +6286,7 @@ som_slurp_armap (bfd *abfd) As part of the prep work we need to determine the number of symbols and the size of the associated string section. */ -static bfd_boolean +static bool som_bfd_prep_for_ar_write (bfd *abfd, unsigned int *num_syms, unsigned int *stringsize) @@ -6231,7 +6315,7 @@ som_bfd_prep_for_ar_write (bfd *abfd, to it. It's a little slimey to grab the symbols via obj_som_symtab, but doing so avoids allocating lots of extra memory. */ if (! som_slurp_symbol_table (curr_bfd)) - return FALSE; + return false; sym = obj_som_symtab (curr_bfd); curr_count = bfd_get_symcount (curr_bfd); @@ -6270,7 +6354,7 @@ som_bfd_prep_for_ar_write (bfd *abfd, curr_bfd = curr_bfd->archive_next; } - return TRUE; + return true; } /* Hash a symbol name based on the hashing algorithm presented in the @@ -6292,7 +6376,7 @@ som_bfd_ar_symbol_hash (asymbol *symbol) /* Do the bulk of the work required to write the SOM library symbol table. */ -static bfd_boolean +static bool som_bfd_ar_write_symbol_stuff (bfd *abfd, unsigned int nsyms, unsigned int string_size, @@ -6306,23 +6390,38 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, struct som_external_som_entry *som_dict = NULL; struct som_external_lst_symbol_record **last_hash_entry = NULL; unsigned int curr_som_offset, som_index = 0; - bfd_size_type amt; + size_t amt; unsigned int module_count; unsigned int hash_size; hash_size = bfd_getb32 (lst.hash_size); - amt = hash_size * 4; + if (_bfd_mul_overflow (hash_size, 4, &amt)) + { + bfd_set_error (bfd_error_no_memory); + return false; + } hash_table = bfd_zmalloc (amt); if (hash_table == NULL && hash_size != 0) goto error_return; module_count = bfd_getb32 (lst.module_count); - amt = module_count * sizeof (struct som_external_som_entry); + if (_bfd_mul_overflow (module_count, + sizeof (struct som_external_som_entry), &amt)) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } som_dict = bfd_zmalloc (amt); if (som_dict == NULL && module_count != 0) goto error_return; - amt = hash_size * sizeof (struct som_external_lst_symbol_record *); + if (_bfd_mul_overflow (hash_size, + sizeof (struct som_external_lst_symbol_record *), + &amt)) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } last_hash_entry = bfd_zmalloc (amt); if (last_hash_entry == NULL && hash_size != 0) goto error_return; @@ -6351,12 +6450,16 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, curr_som_offset = (curr_som_offset + 0x1) & ~0x1; /* FIXME should be done with buffers just like everything else... */ - amt = nsyms; - amt *= sizeof (struct som_external_lst_symbol_record); + if (_bfd_mul_overflow (nsyms, + sizeof (struct som_external_lst_symbol_record), &amt)) + { + bfd_set_error (bfd_error_no_memory); + goto error_return; + } lst_syms = bfd_malloc (amt); if (lst_syms == NULL && nsyms != 0) goto error_return; - strings = bfd_malloc ((bfd_size_type) string_size); + strings = bfd_malloc (string_size); if (strings == NULL && string_size != 0) goto error_return; @@ -6389,11 +6492,11 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, for (i = 0; i < curr_count; i++, sym++) { struct som_misc_symbol_info info; - struct som_external_lst_symbol_record *last; - unsigned int symbol_pos; - unsigned int slen; - unsigned int symbol_key; - unsigned int flags; + struct som_external_lst_symbol_record *last; + unsigned int symbol_pos; + unsigned int slen; + unsigned int symbol_key; + unsigned int flags; /* Derive SOM information from the BFD symbol. */ som_bfd_derive_misc_symbol_info (curr_bfd, &sym->symbol, &info); @@ -6421,40 +6524,40 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, bfd_putb32 (arelt_size (curr_bfd), som_dict[som_index].length); } - symbol_key = som_bfd_ar_symbol_hash (&sym->symbol); + symbol_key = som_bfd_ar_symbol_hash (&sym->symbol); /* Fill in the lst symbol record. */ - flags = 0; - if (info.secondary_def) - flags |= LST_SYMBOL_SECONDARY_DEF; - flags |= info.symbol_type << LST_SYMBOL_SYMBOL_TYPE_SH; - flags |= info.symbol_scope << LST_SYMBOL_SYMBOL_SCOPE_SH; - if (bfd_is_com_section (sym->symbol.section)) - flags |= LST_SYMBOL_IS_COMMON; - if (info.dup_common) - flags |= LST_SYMBOL_DUP_COMMON; - flags |= 3 << LST_SYMBOL_XLEAST_SH; - flags |= info.arg_reloc << LST_SYMBOL_ARG_RELOC_SH; - bfd_putb32 (flags, curr_lst_sym->flags); - bfd_putb32 (p - strings + 4, curr_lst_sym->name); - bfd_putb32 (0, curr_lst_sym->qualifier_name); - bfd_putb32 (info.symbol_info, curr_lst_sym->symbol_info); - bfd_putb32 (info.symbol_value | info.priv_level, - curr_lst_sym->symbol_value); - bfd_putb32 (0, curr_lst_sym->symbol_descriptor); - curr_lst_sym->reserved = 0; - bfd_putb32 (som_index, curr_lst_sym->som_index); - bfd_putb32 (symbol_key, curr_lst_sym->symbol_key); - bfd_putb32 (0, curr_lst_sym->next_entry); + flags = 0; + if (info.secondary_def) + flags |= LST_SYMBOL_SECONDARY_DEF; + flags |= info.symbol_type << LST_SYMBOL_SYMBOL_TYPE_SH; + flags |= info.symbol_scope << LST_SYMBOL_SYMBOL_SCOPE_SH; + if (bfd_is_com_section (sym->symbol.section)) + flags |= LST_SYMBOL_IS_COMMON; + if (info.dup_common) + flags |= LST_SYMBOL_DUP_COMMON; + flags |= 3 << LST_SYMBOL_XLEAST_SH; + flags |= info.arg_reloc << LST_SYMBOL_ARG_RELOC_SH; + bfd_putb32 (flags, curr_lst_sym->flags); + bfd_putb32 (p - strings + 4, curr_lst_sym->name); + bfd_putb32 (0, curr_lst_sym->qualifier_name); + bfd_putb32 (info.symbol_info, curr_lst_sym->symbol_info); + bfd_putb32 (info.symbol_value | info.priv_level, + curr_lst_sym->symbol_value); + bfd_putb32 (0, curr_lst_sym->symbol_descriptor); + curr_lst_sym->reserved = 0; + bfd_putb32 (som_index, curr_lst_sym->som_index); + bfd_putb32 (symbol_key, curr_lst_sym->symbol_key); + bfd_putb32 (0, curr_lst_sym->next_entry); /* Insert into the hash table. */ - symbol_pos = - (curr_lst_sym - lst_syms) - * sizeof (struct som_external_lst_symbol_record) - + hash_size * 4 - + module_count * sizeof (struct som_external_som_entry) - + sizeof (struct som_external_lst_header); - last = last_hash_entry[symbol_key % hash_size]; + symbol_pos = + (curr_lst_sym - lst_syms) + * sizeof (struct som_external_lst_symbol_record) + + hash_size * 4 + + module_count * sizeof (struct som_external_som_entry) + + sizeof (struct som_external_lst_header); + last = last_hash_entry[symbol_key % hash_size]; if (last != NULL) { /* There is already something at the head of this hash chain, @@ -6463,26 +6566,26 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, } else /* First entry in this hash chain. */ - bfd_putb32 (symbol_pos, hash_table + 4 * (symbol_key % hash_size)); + bfd_putb32 (symbol_pos, hash_table + 4 * (symbol_key % hash_size)); /* Keep track of the last symbol we added to this chain so we can easily update its next_entry pointer. */ - last_hash_entry[symbol_key % hash_size] = curr_lst_sym; + last_hash_entry[symbol_key % hash_size] = curr_lst_sym; /* Update the string table. */ - slen = strlen (sym->symbol.name); + slen = strlen (sym->symbol.name); bfd_put_32 (abfd, slen, p); p += 4; - slen++; /* Nul terminator. */ + slen++; /* Nul terminator. */ memcpy (p, sym->symbol.name, slen); p += slen; while (slen % 4) { bfd_put_8 (abfd, 0, p); p++; - slen++; + slen++; } - BFD_ASSERT (p <= strings + string_size); + BFD_ASSERT (p <= strings + string_size); /* Head to the next symbol. */ curr_lst_sym++; @@ -6501,17 +6604,17 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, } /* Now scribble out the hash table. */ - amt = hash_size * 4; + amt = (size_t) hash_size * 4; if (bfd_bwrite ((void *) hash_table, amt, abfd) != amt) goto error_return; /* Then the SOM dictionary. */ - amt = module_count * sizeof (struct som_external_som_entry); + amt = (size_t) module_count * sizeof (struct som_external_som_entry); if (bfd_bwrite ((void *) som_dict, amt, abfd) != amt) goto error_return; /* The library symbols. */ - amt = nsyms * sizeof (struct som_external_lst_symbol_record); + amt = (size_t) nsyms * sizeof (struct som_external_lst_symbol_record); if (bfd_bwrite ((void *) lst_syms, amt, abfd) != amt) goto error_return; @@ -6520,38 +6623,28 @@ som_bfd_ar_write_symbol_stuff (bfd *abfd, if (bfd_bwrite ((void *) strings, amt, abfd) != amt) goto error_return; - if (hash_table != NULL) - free (hash_table); - if (som_dict != NULL) - free (som_dict); - if (last_hash_entry != NULL) - free (last_hash_entry); - if (lst_syms != NULL) - free (lst_syms); - if (strings != NULL) - free (strings); - return TRUE; + free (hash_table); + free (som_dict); + free (last_hash_entry); + free (lst_syms); + free (strings); + return true; error_return: - if (hash_table != NULL) - free (hash_table); - if (som_dict != NULL) - free (som_dict); - if (last_hash_entry != NULL) - free (last_hash_entry); - if (lst_syms != NULL) - free (lst_syms); - if (strings != NULL) - free (strings); - - return FALSE; + free (hash_table); + free (som_dict); + free (last_hash_entry); + free (lst_syms); + free (strings); + + return false; } /* Write out the LST for the archive. You'll never believe this is really how armaps are handled in SOM... */ -static bfd_boolean +static bool som_write_armap (bfd *abfd, unsigned int elength, struct orl *map ATTRIBUTE_UNUSED, @@ -6564,15 +6657,15 @@ som_write_armap (bfd *abfd, struct ar_hdr hdr; struct som_external_lst_header lst; unsigned char *p; - bfd_size_type amt; + size_t amt; unsigned int csum; unsigned int module_count; /* We'll use this for the archive's date and mode later. */ - if (stat (abfd->filename, &statbuf) != 0) + if (stat (bfd_get_filename (abfd), &statbuf) != 0) { bfd_set_error (bfd_error_system_call); - return FALSE; + return false; } /* Fudge factor. */ bfd_ardata (abfd)->armap_timestamp = statbuf.st_mtime + 60; @@ -6624,7 +6717,7 @@ som_write_armap (bfd *abfd, /* Count how many symbols we will have on the hash chains and the size of the associated string table. */ if (! som_bfd_prep_for_ar_write (abfd, &nsyms, &stringsize)) - return FALSE; + return false; lst_size += sizeof (struct som_external_lst_symbol_record) * nsyms; @@ -6649,15 +6742,15 @@ som_write_armap (bfd *abfd, sprintf (hdr.ar_name, "/ "); _bfd_ar_spacepad (hdr.ar_date, sizeof (hdr.ar_date), "%-12ld", - bfd_ardata (abfd)->armap_timestamp); + bfd_ardata (abfd)->armap_timestamp); _bfd_ar_spacepad (hdr.ar_uid, sizeof (hdr.ar_uid), "%ld", - statbuf.st_uid); + statbuf.st_uid); _bfd_ar_spacepad (hdr.ar_gid, sizeof (hdr.ar_gid), "%ld", - statbuf.st_gid); + statbuf.st_gid); _bfd_ar_spacepad (hdr.ar_mode, sizeof (hdr.ar_mode), "%-8o", - (unsigned int)statbuf.st_mode); + (unsigned int)statbuf.st_mode); _bfd_ar_spacepad (hdr.ar_size, sizeof (hdr.ar_size), "%-10d", - (int) lst_size); + (int) lst_size); hdr.ar_fmag[0] = '`'; hdr.ar_fmag[1] = '\012'; @@ -6669,97 +6762,99 @@ som_write_armap (bfd *abfd, /* Scribble out the ar header. */ amt = sizeof (struct ar_hdr); if (bfd_bwrite ((void *) &hdr, amt, abfd) != amt) - return FALSE; + return false; /* Now scribble out the lst header. */ amt = sizeof (struct som_external_lst_header); if (bfd_bwrite ((void *) &lst, amt, abfd) != amt) - return FALSE; + return false; /* Build and write the armap. */ if (!som_bfd_ar_write_symbol_stuff (abfd, nsyms, stringsize, lst, elength)) - return FALSE; + return false; /* Done. */ - return TRUE; + return true; } /* Free all information we have cached for this BFD. We can always read it again later if we need it. */ -static bfd_boolean +static bool som_bfd_free_cached_info (bfd *abfd) { - asection *o; - - if (bfd_get_format (abfd) != bfd_object) - return TRUE; - -#define FREE(x) if (x != NULL) { free (x); x = NULL; } - /* Free the native string and symbol tables. */ - FREE (obj_som_symtab (abfd)); - FREE (obj_som_stringtab (abfd)); - for (o = abfd->sections; o != NULL; o = o->next) + if (bfd_get_format (abfd) == bfd_object) { - /* Free the native relocations. */ - o->reloc_count = (unsigned) -1; - FREE (som_section_data (o)->reloc_stream); - /* Do not free the generic relocations as they are objalloc'ed. */ - } + asection *o; + +#define FREE(x) do { free (x); x = NULL; } while (0) + /* Free the native string and symbol tables. */ + FREE (obj_som_symtab (abfd)); + FREE (obj_som_stringtab (abfd)); + for (o = abfd->sections; o != NULL; o = o->next) + { + /* Free the native relocations. */ + o->reloc_count = (unsigned) -1; + FREE (som_section_data (o)->reloc_stream); + /* Do not free the generic relocations as they are objalloc'ed. */ + } #undef FREE + } - return TRUE; + return _bfd_generic_close_and_cleanup (abfd); } /* End of miscellaneous support functions. */ /* Linker support functions. */ -static bfd_boolean +static bool som_bfd_link_split_section (bfd *abfd ATTRIBUTE_UNUSED, asection *sec) { return som_is_subspace (sec) && sec->size > 240000; } -#define som_find_line _bfd_nosymbols_find_line +#define som_find_line _bfd_nosymbols_find_line #define som_get_symbol_version_string _bfd_nosymbols_get_symbol_version_string -#define som_close_and_cleanup som_bfd_free_cached_info -#define som_read_ar_hdr _bfd_generic_read_ar_hdr -#define som_write_ar_hdr _bfd_generic_write_ar_hdr -#define som_openr_next_archived_file bfd_generic_openr_next_archived_file -#define som_get_elt_at_index _bfd_generic_get_elt_at_index -#define som_generic_stat_arch_elt bfd_generic_stat_arch_elt -#define som_truncate_arname bfd_bsd_truncate_arname -#define som_slurp_extended_name_table _bfd_slurp_extended_name_table -#define som_construct_extended_name_table _bfd_archive_coff_construct_extended_name_table -#define som_update_armap_timestamp bfd_true -#define som_bfd_is_target_special_symbol ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false) -#define som_get_lineno _bfd_nosymbols_get_lineno -#define som_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol -#define som_read_minisymbols _bfd_generic_read_minisymbols -#define som_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol -#define som_get_section_contents_in_window _bfd_generic_get_section_contents_in_window -#define som_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents -#define som_bfd_relax_section bfd_generic_relax_section -#define som_bfd_link_hash_table_create _bfd_generic_link_hash_table_create -#define som_bfd_link_add_symbols _bfd_generic_link_add_symbols -#define som_bfd_link_just_syms _bfd_generic_link_just_syms +#define som_close_and_cleanup som_bfd_free_cached_info +#define som_read_ar_hdr _bfd_generic_read_ar_hdr +#define som_write_ar_hdr _bfd_generic_write_ar_hdr +#define som_openr_next_archived_file bfd_generic_openr_next_archived_file +#define som_get_elt_at_index _bfd_generic_get_elt_at_index +#define som_generic_stat_arch_elt bfd_generic_stat_arch_elt +#define som_truncate_arname bfd_bsd_truncate_arname +#define som_slurp_extended_name_table _bfd_slurp_extended_name_table +#define som_construct_extended_name_table _bfd_archive_coff_construct_extended_name_table +#define som_update_armap_timestamp _bfd_bool_bfd_true +#define som_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false +#define som_get_lineno _bfd_nosymbols_get_lineno +#define som_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol +#define som_read_minisymbols _bfd_generic_read_minisymbols +#define som_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol +#define som_get_section_contents_in_window _bfd_generic_get_section_contents_in_window +#define som_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents +#define som_bfd_relax_section bfd_generic_relax_section +#define som_bfd_link_hash_table_create _bfd_generic_link_hash_table_create +#define som_bfd_link_add_symbols _bfd_generic_link_add_symbols +#define som_bfd_link_just_syms _bfd_generic_link_just_syms #define som_bfd_copy_link_hash_symbol_type \ _bfd_generic_copy_link_hash_symbol_type -#define som_bfd_final_link _bfd_generic_final_link -#define som_bfd_gc_sections bfd_generic_gc_sections -#define som_bfd_lookup_section_flags bfd_generic_lookup_section_flags -#define som_bfd_merge_sections bfd_generic_merge_sections -#define som_bfd_is_group_section bfd_generic_is_group_section -#define som_bfd_discard_group bfd_generic_discard_group -#define som_section_already_linked _bfd_generic_section_already_linked -#define som_bfd_define_common_symbol bfd_generic_define_common_symbol -#define som_bfd_define_start_stop bfd_generic_define_start_stop +#define som_bfd_final_link _bfd_generic_final_link +#define som_bfd_gc_sections bfd_generic_gc_sections +#define som_bfd_lookup_section_flags bfd_generic_lookup_section_flags +#define som_bfd_merge_sections bfd_generic_merge_sections +#define som_bfd_is_group_section bfd_generic_is_group_section +#define som_bfd_group_name bfd_generic_group_name +#define som_bfd_discard_group bfd_generic_discard_group +#define som_section_already_linked _bfd_generic_section_already_linked +#define som_bfd_define_common_symbol bfd_generic_define_common_symbol +#define som_bfd_link_hide_symbol _bfd_generic_link_hide_symbol +#define som_bfd_define_start_stop bfd_generic_define_start_stop #define som_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data #define som_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data #define som_bfd_set_private_flags _bfd_generic_bfd_set_private_flags #define som_find_inliner_info _bfd_nosymbols_find_inliner_info -#define som_bfd_link_check_relocs _bfd_generic_link_check_relocs +#define som_bfd_link_check_relocs _bfd_generic_link_check_relocs #define som_set_reloc _bfd_generic_set_reloc const bfd_target hppa_som_vec = @@ -6780,6 +6875,7 @@ const bfd_target hppa_som_vec = '/', /* AR_pad_char. */ 14, /* AR_max_namelen. */ 0, /* match priority. */ + TARGET_KEEP_UNUSED_SECTION_SYMBOLS, /* keep unused section symbols. */ bfd_getb64, bfd_getb_signed_64, bfd_putb64, bfd_getb32, bfd_getb_signed_32, bfd_putb32, bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* Data. */ @@ -6792,16 +6888,16 @@ const bfd_target hppa_som_vec = _bfd_dummy_target }, { - bfd_false, + _bfd_bool_bfd_false_error, som_mkobject, _bfd_generic_mkarchive, - bfd_false + _bfd_bool_bfd_false_error }, { - bfd_false, + _bfd_bool_bfd_false_error, som_write_object_contents, _bfd_write_archive_contents, - bfd_false, + _bfd_bool_bfd_false_error, }, #undef som