/* Generic BFD library interface and support routines.
   Copyright (C) 1990-2024 Free Software Foundation, Inc.
   Written by Cygnus Support.

   This file is part of BFD, the Binary File Descriptor library.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
   MA 02110-1301, USA.  */

/*
INODE
typedef bfd, Error reporting, BFD front end, BFD front end

SECTION
	<<typedef bfd>>

	A BFD has type <<bfd>>; objects of this type are the
	cornerstone of any application using BFD. Using BFD
	consists of making references though the BFD and to data in the BFD.

	Here is the structure that defines the type <<bfd>>.  It
	contains the major data about the file and pointers
	to the rest of the data.

EXTERNAL
.typedef enum bfd_format
.  {
.    bfd_unknown = 0,	{* File format is unknown.  *}
.    bfd_object,	{* Linker/assembler/compiler output.  *}
.    bfd_archive,	{* Object archive file.  *}
.    bfd_core,		{* Core dump.  *}
.    bfd_type_end	{* Marks the end; don't use it!  *}
.  }
.bfd_format;
.
.enum bfd_direction
.  {
.    no_direction = 0,
.    read_direction = 1,
.    write_direction = 2,
.    both_direction = 3
.  };
.
.enum bfd_last_io
.  {
.    bfd_io_seek = 0,
.    bfd_io_read = 1,
.    bfd_io_write = 2,
.    bfd_io_force = 3
.  };
.
.enum bfd_plugin_format
.  {
.    bfd_plugin_unknown = 0,
.    bfd_plugin_yes = 1,
.    bfd_plugin_yes_unused = 2,
.    bfd_plugin_no = 3
.  };
.
.struct bfd_build_id
.  {
.    bfd_size_type size;
.    bfd_byte data[1];
.  };
.
.enum bfd_lto_object_type
.  {
.    lto_non_object,		{* Not an LTO object.  *}
.    lto_non_ir_object,		{* An object without LTO IR.  *}
.    lto_slim_ir_object,	{* A slim LTO IR object.  *}
.    lto_fat_ir_object		{* A fat LTO IR object.  *}
.  };
.
.struct bfd_mmapped_entry
.  {
.    void *addr;
.    size_t size;
.  };
.
.struct bfd_mmapped
.  {
.    struct bfd_mmapped *next;
.    unsigned int max_entry;
.    unsigned int next_entry;
.    struct bfd_mmapped_entry entries[1];
.  };
.

CODE_FRAGMENT
.struct bfd
.{
.  {* The filename the application opened the BFD with.  *}
.  const char *filename;
.
.  {* A pointer to the target jump table.  *}
.  const struct bfd_target *xvec;
.
.  {* The IOSTREAM, and corresponding IO vector that provide access
.     to the file backing the BFD.  *}
.  void *iostream;
.  const struct bfd_iovec *iovec;
.
.  {* The caching routines use these to maintain a
.     least-recently-used list of BFDs.  *}
.  struct bfd *lru_prev, *lru_next;
.
.  {* Track current file position (or current buffer offset for
.     in-memory BFDs).  When a file is closed by the caching routines,
.     BFD retains state information on the file here.  *}
.  ufile_ptr where;
.
.  {* File modified time, if mtime_set is TRUE.  *}
.  long mtime;
.
.  {* A unique identifier of the BFD  *}
.  unsigned int id;
.
.  {* Format_specific flags.  *}
.  flagword flags;
.
.  {* Values that may appear in the flags field of a BFD.  These also
.     appear in the object_flags field of the bfd_target structure, where
.     they indicate the set of flags used by that backend (not all flags
.     are meaningful for all object file formats) (FIXME: at the moment,
.     the object_flags values have mostly just been copied from backend
.     to another, and are not necessarily correct).  *}
.
.#define BFD_NO_FLAGS                0x0
.
.  {* BFD contains relocation entries.  *}
.#define HAS_RELOC                   0x1
.
.  {* BFD is directly executable.  *}
.#define EXEC_P                      0x2
.
.  {* BFD has line number information (basically used for F_LNNO in a
.     COFF header).  *}
.#define HAS_LINENO                  0x4
.
.  {* BFD has debugging information.  *}
.#define HAS_DEBUG                  0x08
.
.  {* BFD has symbols.  *}
.#define HAS_SYMS                   0x10
.
.  {* BFD has local symbols (basically used for F_LSYMS in a COFF
.     header).  *}
.#define HAS_LOCALS                 0x20
.
.  {* BFD is a dynamic object.  *}
.#define DYNAMIC                    0x40
.
.  {* Text section is write protected (if D_PAGED is not set, this is
.     like an a.out NMAGIC file) (the linker sets this by default, but
.     clears it for -r or -N).  *}
.#define WP_TEXT                    0x80
.
.  {* BFD is dynamically paged (this is like an a.out ZMAGIC file) (the
.     linker sets this by default, but clears it for -r or -n or -N).  *}
.#define D_PAGED                   0x100
.
.  {* BFD is relaxable (this means that bfd_relax_section may be able to
.     do something) (sometimes bfd_relax_section can do something even if
.     this is not set).  *}
.#define BFD_IS_RELAXABLE          0x200
.
.  {* This may be set before writing out a BFD to request using a
.     traditional format.  For example, this is used to request that when
.     writing out an a.out object the symbols not be hashed to eliminate
.     duplicates.  *}
.#define BFD_TRADITIONAL_FORMAT    0x400
.
.  {* This flag indicates that the BFD contents are actually cached
.     in memory.  If this is set, iostream points to a malloc'd
.     bfd_in_memory struct.  *}
.#define BFD_IN_MEMORY             0x800
.
.  {* This BFD has been created by the linker and doesn't correspond
.     to any input file.  *}
.#define BFD_LINKER_CREATED       0x1000
.
.  {* This may be set before writing out a BFD to request that it
.     be written using values for UIDs, GIDs, timestamps, etc. that
.     will be consistent from run to run.  *}
.#define BFD_DETERMINISTIC_OUTPUT 0x2000
.
.  {* Compress sections in this BFD.  *}
.#define BFD_COMPRESS             0x4000
.
.  {* Decompress sections in this BFD.  *}
.#define BFD_DECOMPRESS           0x8000
.
.  {* BFD is a dummy, for plugins.  *}
.#define BFD_PLUGIN              0x10000
.
.  {* Compress sections in this BFD with SHF_COMPRESSED from gABI.  *}
.#define BFD_COMPRESS_GABI       0x20000
.
.  {* Convert ELF common symbol type to STT_COMMON or STT_OBJECT in this
.     BFD.  *}
.#define BFD_CONVERT_ELF_COMMON  0x40000
.
.  {* Use the ELF STT_COMMON type in this BFD.  *}
.#define BFD_USE_ELF_STT_COMMON  0x80000
.
.  {* Put pathnames into archives (non-POSIX).  *}
.#define BFD_ARCHIVE_FULL_PATH  0x100000
.
.#define BFD_CLOSED_BY_CACHE    0x200000

.  {* Compress sections in this BFD with SHF_COMPRESSED zstd.  *}
.#define BFD_COMPRESS_ZSTD      0x400000
.
.  {* Don't generate ELF section header.  *}
.#define BFD_NO_SECTION_HEADER	0x800000
.
.  {* Flags bits which are for BFD use only.  *}
.#define BFD_FLAGS_FOR_BFD_USE_MASK \
.  (BFD_IN_MEMORY | BFD_COMPRESS | BFD_DECOMPRESS | BFD_LINKER_CREATED \
.   | BFD_PLUGIN | BFD_TRADITIONAL_FORMAT | BFD_DETERMINISTIC_OUTPUT \
.   | BFD_COMPRESS_GABI | BFD_CONVERT_ELF_COMMON | BFD_USE_ELF_STT_COMMON \
.   | BFD_NO_SECTION_HEADER)
.
.  {* The format which belongs to the BFD. (object, core, etc.)  *}
.  ENUM_BITFIELD (bfd_format) format : 3;
.
.  {* The direction with which the BFD was opened.  *}
.  ENUM_BITFIELD (bfd_direction) direction : 2;
.
.  {* POSIX.1-2017 (IEEE Std 1003.1) says of fopen : "When a file is
.     opened with update mode ('+' as the second or third character in
.     the mode argument), both input and output may be performed on
.     the associated stream.  However, the application shall ensure
.     that output is not directly followed by input without an
.     intervening call to fflush() or to a file positioning function
.     (fseek(), fsetpos(), or rewind()), and input is not directly
.     followed by output without an intervening call to a file
.     positioning function, unless the input operation encounters
.     end-of-file."
.     This field tracks the last IO operation, so that bfd can insert
.     a seek when IO direction changes.  *}
.  ENUM_BITFIELD (bfd_last_io) last_io : 2;
.
.  {* Is the file descriptor being cached?  That is, can it be closed as
.     needed, and re-opened when accessed later?  *}
.  unsigned int cacheable : 1;
.
.  {* Marks whether there was a default target specified when the
.     BFD was opened. This is used to select which matching algorithm
.     to use to choose the back end.  *}
.  unsigned int target_defaulted : 1;
.
.  {* ... and here: (``once'' means at least once).  *}
.  unsigned int opened_once : 1;
.
.  {* Set if we have a locally maintained mtime value, rather than
.     getting it from the file each time.  *}
.  unsigned int mtime_set : 1;
.
.  {* Flag set if symbols from this BFD should not be exported.  *}
.  unsigned int no_export : 1;
.
.  {* Remember when output has begun, to stop strange things
.     from happening.  *}
.  unsigned int output_has_begun : 1;
.
.  {* Have archive map.  *}
.  unsigned int has_armap : 1;
.
.  {* Set if this is a thin archive.  *}
.  unsigned int is_thin_archive : 1;
.
.  {* Set if this archive should not cache element positions.  *}
.  unsigned int no_element_cache : 1;
.
.  {* Set if only required symbols should be added in the link hash table for
.     this object.  Used by VMS linkers.  *}
.  unsigned int selective_search : 1;
.
.  {* Set if this is the linker output BFD.  *}
.  unsigned int is_linker_output : 1;
.
.  {* Set if this is the linker input BFD.  *}
.  unsigned int is_linker_input : 1;
.
.  {* If this is an input for a compiler plug-in library.  *}
.  ENUM_BITFIELD (bfd_plugin_format) plugin_format : 2;
.
.  {* Set if this is a plugin output file.  *}
.  unsigned int lto_output : 1;
.
.  {* Do not attempt to modify this file.  Set when detecting errors
.     that BFD is not prepared to handle for objcopy/strip.  *}
.  unsigned int read_only : 1;
.
.  {* LTO object type.  *}
.  ENUM_BITFIELD (bfd_lto_object_type) lto_type : 2;
.
.  {* Set if this BFD is currently being processed by
.     bfd_check_format_matches.  This is checked by the cache to
.     avoid closing the BFD in this case.  This should only be
.     examined or modified while the BFD lock is held.  *}
.  unsigned int in_format_matches : 1;
.
.  {* Set to dummy BFD created when claimed by a compiler plug-in
.     library.  *}
.  bfd *plugin_dummy_bfd;
.
.  {* The offset of this bfd in the file, typically 0 if it is not
.     contained in an archive.  *}
.  ufile_ptr origin;
.
.  {* The origin in the archive of the proxy entry.  This will
.     normally be the same as origin, except for thin archives,
.     when it will contain the current offset of the proxy in the
.     thin archive rather than the offset of the bfd in its actual
.     container.  *}
.  ufile_ptr proxy_origin;
.
.  {* A hash table for section names.  *}
.  struct bfd_hash_table section_htab;
.
.  {* Pointer to linked list of sections.  *}
.  struct bfd_section *sections;
.
.  {* The last section on the section list.  *}
.  struct bfd_section *section_last;
.
.  {* The number of sections.  *}
.  unsigned int section_count;
.
.  {* The archive plugin file descriptor.  *}
.  int archive_plugin_fd;
.
.  {* The number of opens on the archive plugin file descriptor.  *}
.  unsigned int archive_plugin_fd_open_count;
.
.  {* A field used by _bfd_generic_link_add_archive_symbols.  This will
.     be used only for archive elements.  *}
.  int archive_pass;
.
.  {* The total size of memory from bfd_alloc.  *}
.  bfd_size_type alloc_size;
.
.  {* Stuff only useful for object files:
.     The start address.  *}
.  bfd_vma start_address;
.
.  {* Symbol table for output BFD (with symcount entries).
.     Also used by the linker to cache input BFD symbols.  *}
.  struct bfd_symbol **outsymbols;
.
.  {* Used for input and output.  *}
.  unsigned int symcount;
.
.  {* Used for slurped dynamic symbol tables.  *}
.  unsigned int dynsymcount;
.
.  {* Pointer to structure which contains architecture information.  *}
.  const struct bfd_arch_info *arch_info;
.
.  {* Cached length of file for bfd_get_size.  0 until bfd_get_size is
.     called, 1 if stat returns an error or the file size is too large to
.     return in ufile_ptr.  Both 0 and 1 should be treated as "unknown".  *}
.  ufile_ptr size;
.
.  {* Stuff only useful for archives.  *}
.  void *arelt_data;
.  struct bfd *my_archive;      {* The containing archive BFD.  *}
.  struct bfd *archive_next;    {* The next BFD in the archive.  *}
.  struct bfd *archive_head;    {* The first BFD in the archive.  *}
.  struct bfd *nested_archives; {* List of nested archive in a flattened
.				   thin archive.  *}
.
.  union {
.    {* For input BFDs, a chain of BFDs involved in a link.  *}
.    struct bfd *next;
.    {* For output BFD, the linker hash table.  *}
.    struct bfd_link_hash_table *hash;
.  } link;
.
.  {* Used by the back end to hold private data.  *}
.  union
.    {
.      struct aout_data_struct *aout_data;
.      struct artdata *aout_ar_data;
.      struct coff_tdata *coff_obj_data;
.      struct pe_tdata *pe_obj_data;
.      struct xcoff_tdata *xcoff_obj_data;
.      struct ecoff_tdata *ecoff_obj_data;
.      struct srec_data_struct *srec_data;
.      struct verilog_data_struct *verilog_data;
.      struct ihex_data_struct *ihex_data;
.      struct tekhex_data_struct *tekhex_data;
.      struct elf_obj_tdata *elf_obj_data;
.      struct mmo_data_struct *mmo_data;
.      struct trad_core_struct *trad_core_data;
.      struct som_data_struct *som_data;
.      struct hpux_core_struct *hpux_core_data;
.      struct hppabsd_core_struct *hppabsd_core_data;
.      struct sgi_core_struct *sgi_core_data;
.      struct lynx_core_struct *lynx_core_data;
.      struct osf_core_struct *osf_core_data;
.      struct cisco_core_struct *cisco_core_data;
.      struct netbsd_core_struct *netbsd_core_data;
.      struct mach_o_data_struct *mach_o_data;
.      struct mach_o_fat_data_struct *mach_o_fat_data;
.      struct plugin_data_struct *plugin_data;
.      struct bfd_pef_data_struct *pef_data;
.      struct bfd_pef_xlib_data_struct *pef_xlib_data;
.      struct bfd_sym_data_struct *sym_data;
.      void *any;
.    }
.  tdata;
.
.  {* Used by the application to hold private data.  *}
.  void *usrdata;
.
.  {* Where all the allocated stuff under this BFD goes.  This is a
.     struct objalloc *, but we use void * to avoid requiring the inclusion
.     of objalloc.h.  *}
.  void *memory;
.
.  {* For input BFDs, the build ID, if the object has one. *}
.  const struct bfd_build_id *build_id;
.
.  {* For input BFDs, mmapped entries. *}
.  struct bfd_mmapped *mmapped;
.};
.

EXTERNAL
.static inline const char *
.bfd_get_filename (const bfd *abfd)
.{
.  return abfd->filename;
.}
.
.static inline bool
.bfd_get_cacheable (const bfd *abfd)
.{
.  return abfd->cacheable;
.}
.
.static inline enum bfd_format
.bfd_get_format (const bfd *abfd)
.{
.  return abfd->format;
.}
.
.static inline enum bfd_lto_object_type
.bfd_get_lto_type (const bfd *abfd)
.{
.  return abfd->lto_type;
.}
.
.static inline flagword
.bfd_get_file_flags (const bfd *abfd)
.{
.  return abfd->flags;
.}
.
.static inline bfd_vma
.bfd_get_start_address (const bfd *abfd)
.{
.  return abfd->start_address;
.}
.
.static inline unsigned int
.bfd_get_symcount (const bfd *abfd)
.{
.  return abfd->symcount;
.}
.
.static inline unsigned int
.bfd_get_dynamic_symcount (const bfd *abfd)
.{
.  return abfd->dynsymcount;
.}
.
.static inline struct bfd_symbol **
.bfd_get_outsymbols (const bfd *abfd)
.{
.  return abfd->outsymbols;
.}
.
.static inline unsigned int
.bfd_count_sections (const bfd *abfd)
.{
.  return abfd->section_count;
.}
.
.static inline bool
.bfd_has_map (const bfd *abfd)
.{
.  return abfd->has_armap;
.}
.
.static inline bool
.bfd_is_thin_archive (const bfd *abfd)
.{
.  return abfd->is_thin_archive;
.}
.
.static inline void *
.bfd_usrdata (const bfd *abfd)
.{
.  return abfd->usrdata;
.}
.
.{* See note beside bfd_set_section_userdata.  *}
.static inline bool
.bfd_set_cacheable (bfd * abfd, bool val)
.{
.  abfd->cacheable = val;
.  return true;
.}
.
.static inline void
.bfd_set_thin_archive (bfd *abfd, bool val)
.{
.  abfd->is_thin_archive = val;
.}
.
.static inline void
.bfd_set_usrdata (bfd *abfd, void *val)
.{
.  abfd->usrdata = val;
.}
.
.static inline asection *
.bfd_asymbol_section (const asymbol *sy)
.{
.  return sy->section;
.}
.
.static inline bfd_vma
.bfd_asymbol_value (const asymbol *sy)
.{
.  return sy->section->vma + sy->value;
.}
.
.static inline const char *
.bfd_asymbol_name (const asymbol *sy)
.{
.  return sy->name;
.}
.
.static inline struct bfd *
.bfd_asymbol_bfd (const asymbol *sy)
.{
.  return sy->the_bfd;
.}
.
.static inline void
.bfd_set_asymbol_name (asymbol *sy, const char *name)
.{
.  sy->name = name;
.}
.
.{* For input sections return the original size on disk of the
.   section.  For output sections return the current size.  *}
.static inline bfd_size_type
.bfd_get_section_limit_octets (const bfd *abfd, const asection *sec)
.{
.  if (abfd->direction != write_direction && sec->rawsize != 0)
.    return sec->rawsize;
.  return sec->size;
.}
.
.{* Find the address one past the end of SEC.  *}
.static inline bfd_size_type
.bfd_get_section_limit (const bfd *abfd, const asection *sec)
.{
.  return (bfd_get_section_limit_octets (abfd, sec)
.	   / bfd_octets_per_byte (abfd, sec));
.}
.
.{* For input sections return the larger of the current size and the
.   original size on disk of the section.  For output sections return
.   the current size.  *}
.static inline bfd_size_type
.bfd_get_section_alloc_size (const bfd *abfd, const asection *sec)
.{
.  if (abfd->direction != write_direction && sec->rawsize > sec->size)
.    return sec->rawsize;
.  return sec->size;
.}
.
.{* Functions to handle insertion and deletion of a bfd's sections.  These
.   only handle the list pointers, ie. do not adjust section_count,
.   target_index etc.  *}
.static inline void
.bfd_section_list_remove (bfd *abfd, asection *s)
.{
.  asection *next = s->next;
.  asection *prev = s->prev;
.  if (prev)
.    prev->next = next;
.  else
.    abfd->sections = next;
.  if (next)
.    next->prev = prev;
.  else
.    abfd->section_last = prev;
.}
.
.static inline void
.bfd_section_list_append (bfd *abfd, asection *s)
.{
.  s->next = 0;
.  if (abfd->section_last)
.    {
.      s->prev = abfd->section_last;
.      abfd->section_last->next = s;
.    }
.  else
.    {
.      s->prev = 0;
.      abfd->sections = s;
.    }
.  abfd->section_last = s;
.}
.
.static inline void
.bfd_section_list_prepend (bfd *abfd, asection *s)
.{
.  s->prev = 0;
.  if (abfd->sections)
.    {
.      s->next = abfd->sections;
.      abfd->sections->prev = s;
.    }
.  else
.    {
.      s->next = 0;
.      abfd->section_last = s;
.    }
.  abfd->sections = s;
.}
.
.static inline void
.bfd_section_list_insert_after (bfd *abfd, asection *a, asection *s)
.{
.  asection *next = a->next;
.  s->next = next;
.  s->prev = a;
.  a->next = s;
.  if (next)
.    next->prev = s;
.  else
.    abfd->section_last = s;
.}
.
.static inline void
.bfd_section_list_insert_before (bfd *abfd, asection *b, asection *s)
.{
.  asection *prev = b->prev;
.  s->prev = prev;
.  s->next = b;
.  b->prev = s;
.  if (prev)
.    prev->next = s;
.  else
.    abfd->sections = s;
.}
.
.static inline bool
.bfd_section_removed_from_list (const bfd *abfd, const asection *s)
.{
.  return s->next ? s->next->prev != s : abfd->section_last != s;
.}
.
*/

#include "sysdep.h"
#include <stdarg.h>
#include "bfd.h"
#include "bfdver.h"
#include "libiberty.h"
#include "demangle.h"
#include "safe-ctype.h"
#include "bfdlink.h"
#include "libbfd.h"
#include "coff/internal.h"
#include "coff/sym.h"
#include "libcoff.h"
#include "libecoff.h"
#undef obj_symbols
#include "elf-bfd.h"

#ifndef EXIT_FAILURE
#define EXIT_FAILURE 1
#endif


/* provide storage for subsystem, stack and heap data which may have been
   passed in on the command line.  Ld puts this data into a bfd_link_info
   struct which ultimately gets passed in to the bfd.  When it arrives, copy
   it to the following struct so that the data will be available in coffcode.h
   where it is needed.  The typedef's used are defined in bfd.h */

/*
INODE
Error reporting, Initialization, typedef bfd, BFD front end

SECTION
	Error reporting

	Most BFD functions return nonzero on success (check their
	individual documentation for precise semantics).  On an error,
	they call <<bfd_set_error>> to set an error condition that callers
	can check by calling <<bfd_get_error>>.
	If that returns <<bfd_error_system_call>>, then check
	<<errno>>.

	The easiest way to report a BFD error to the user is to
	use <<bfd_perror>>.

	The BFD error is thread-local.

SUBSECTION
	Type <<bfd_error_type>>

	The values returned by <<bfd_get_error>> are defined by the
	enumerated type <<bfd_error_type>>.

CODE_FRAGMENT
.typedef enum bfd_error
.{
.  bfd_error_no_error = 0,
.  bfd_error_system_call,
.  bfd_error_invalid_target,
.  bfd_error_wrong_format,
.  bfd_error_wrong_object_format,
.  bfd_error_invalid_operation,
.  bfd_error_no_memory,
.  bfd_error_no_symbols,
.  bfd_error_no_armap,
.  bfd_error_no_more_archived_files,
.  bfd_error_malformed_archive,
.  bfd_error_missing_dso,
.  bfd_error_file_not_recognized,
.  bfd_error_file_ambiguously_recognized,
.  bfd_error_no_contents,
.  bfd_error_nonrepresentable_section,
.  bfd_error_no_debug_section,
.  bfd_error_bad_value,
.  bfd_error_file_truncated,
.  bfd_error_file_too_big,
.  bfd_error_sorry,
.  bfd_error_on_input,
.  bfd_error_invalid_error_code
.}
.bfd_error_type;
.
*/

static TLS bfd_error_type bfd_error;
static TLS bfd_error_type input_error;
static TLS bfd *input_bfd;
static TLS char *_bfd_error_buf;

const char *const bfd_errmsgs[] =
{
  N_("no error"),
  N_("system call error"),
  N_("invalid bfd target"),
  N_("file in wrong format"),
  N_("archive object file in wrong format"),
  N_("invalid operation"),
  N_("memory exhausted"),
  N_("no symbols"),
  N_("archive has no index; run ranlib to add one"),
  N_("no more archived files"),
  N_("malformed archive"),
  N_("DSO missing from command line"),
  N_("file format not recognized"),
  N_("file format is ambiguous"),
  N_("section has no contents"),
  N_("nonrepresentable section on output"),
  N_("symbol needs debug section which does not exist"),
  N_("bad value"),
  N_("file truncated"),
  N_("file too big"),
  N_("sorry, cannot handle this file"),
  N_("error reading %s: %s"),
  N_("#<invalid error code>")
};

/*
FUNCTION
	bfd_get_error

SYNOPSIS
	bfd_error_type bfd_get_error (void);

DESCRIPTION
	Return the current BFD error condition.
*/

bfd_error_type
bfd_get_error (void)
{
  return bfd_error;
}

/*
FUNCTION
	bfd_set_error

SYNOPSIS
	void bfd_set_error (bfd_error_type error_tag);

DESCRIPTION
	Set the BFD error condition to be @var{error_tag}.

	@var{error_tag} must not be bfd_error_on_input.  Use
	bfd_set_input_error for input errors instead.
*/

void
bfd_set_error (bfd_error_type error_tag)
{
  bfd_error = error_tag;
  if (bfd_error >= bfd_error_on_input)
    abort ();
}

/*
FUNCTION
	bfd_set_input_error

SYNOPSIS
	void bfd_set_input_error (bfd *input, bfd_error_type error_tag);

DESCRIPTION

	Set the BFD error condition to be bfd_error_on_input.
	@var{input} is the input bfd where the error occurred, and
	@var{error_tag} the bfd_error_type error.
*/

void
bfd_set_input_error (bfd *input, bfd_error_type error_tag)
{
  /* This is an error that occurred during bfd_close when writing an
     archive, but on one of the input files.  */
  bfd_error = bfd_error_on_input;
  _bfd_clear_error_data ();
  input_bfd = input;
  input_error = error_tag;
  if (input_error >= bfd_error_on_input)
    abort ();
}

/*
FUNCTION
	bfd_errmsg

SYNOPSIS
	const char *bfd_errmsg (bfd_error_type error_tag);

DESCRIPTION
	Return a string describing the error @var{error_tag}, or
	the system error if @var{error_tag} is <<bfd_error_system_call>>.
*/

const char *
bfd_errmsg (bfd_error_type error_tag)
{
#ifndef errno
  extern int errno;
#endif
  if (error_tag == bfd_error_on_input)
    {
      const char *msg = bfd_errmsg (input_error);
      char *ret = bfd_asprintf (_(bfd_errmsgs[error_tag]),
				bfd_get_filename (input_bfd), msg);
      if (ret)
	return ret;

      /* Ick, what to do on out of memory?  */
      return msg;
    }

  if (error_tag == bfd_error_system_call)
    return xstrerror (errno);

  if (error_tag > bfd_error_invalid_error_code)
    error_tag = bfd_error_invalid_error_code;	/* sanity check */

  return _(bfd_errmsgs[error_tag]);
}

/*
FUNCTION
	bfd_perror

SYNOPSIS
	void bfd_perror (const char *message);

DESCRIPTION
	Print to the standard error stream a string describing the
	last BFD error that occurred, or the last system error if
	the last BFD error was a system call failure.  If @var{message}
	is non-NULL and non-empty, the error string printed is preceded
	by @var{message}, a colon, and a space.  It is followed by a newline.
*/

void
bfd_perror (const char *message)
{
  fflush (stdout);
  if (message == NULL || *message == '\0')
    fprintf (stderr, "%s\n", bfd_errmsg (bfd_get_error ()));
  else
    fprintf (stderr, "%s: %s\n", message, bfd_errmsg (bfd_get_error ()));
  fflush (stderr);
}

/*
INTERNAL_FUNCTION
	_bfd_clear_error_data

SYNOPSIS
	void _bfd_clear_error_data (void);

DESCRIPTION
	Free any data associated with the BFD error.
*/

void
_bfd_clear_error_data (void)
{
  free (_bfd_error_buf);
  _bfd_error_buf = NULL;
}

/*
INTERNAL_FUNCTION
	bfd_asprintf

SYNOPSIS
	char *bfd_asprintf (const char *fmt, ...);

DESCRIPTION
	Primarily for error reporting, this function is like
	libiberty's xasprintf except that it can return NULL on no
	memory and the returned string should not be freed.  Uses a
	thread-local malloc'd buffer managed by libbfd, _bfd_error_buf.
	Be aware that a call to this function frees the result of any
	previous call.  bfd_errmsg (bfd_error_on_input) also calls
	this function.
*/

char *
bfd_asprintf (const char *fmt, ...)
{
  free (_bfd_error_buf);
  _bfd_error_buf = NULL;
  va_list ap;
  va_start (ap, fmt);
  int count = vasprintf (&_bfd_error_buf, fmt, ap);
  va_end (ap);
  if (count == -1)
    {
      bfd_set_error (bfd_error_no_memory);
      _bfd_error_buf = NULL;
    }
  return _bfd_error_buf;
}

/*
SUBSECTION
	BFD error handler

	Some BFD functions want to print messages describing the
	problem.  They call a BFD error handler function.  This
	function may be overridden by the program.

	The BFD error handler acts like vprintf.

CODE_FRAGMENT
.typedef void (*bfd_error_handler_type) (const char *, va_list);
.
*/

/* The program name used when printing BFD error messages.  */

static const char *_bfd_error_program_name;

/* Support for positional parameters.  */

union _bfd_doprnt_args
{
  int i;
  long l;
  long long ll;
  double d;
  long double ld;
  void *p;
  enum
  {
    Bad,
    Int,
    Long,
    LongLong,
    Double,
    LongDouble,
    Ptr
  } type;
};

/* Maximum number of _bfd_error_handler args.  Don't increase this
   without changing the code handling positional parameters.  */
#define MAX_ARGS 9

/* This macro and _bfd_doprnt taken from libiberty _doprnt.c, tidied a
   little and extended to handle '%pA', '%pB' and positional parameters.  */

#define PRINT_TYPE(TYPE, FIELD) \
  do								\
    {								\
      TYPE value = (TYPE) args[arg_no].FIELD;			\
      result = print (stream, specifier, value);		\
    } while (0)

/*
CODE_FRAGMENT
.typedef int (*bfd_print_callback) (void *, const char *, ...);
*/

static int
_bfd_doprnt (bfd_print_callback print, void *stream, const char *format,
	     union _bfd_doprnt_args *args)
{
  const char *ptr = format;
  char specifier[128];
  int total_printed = 0;
  unsigned int arg_count = 0;

  while (*ptr != '\0')
    {
      int result;

      if (*ptr != '%')
	{
	  /* While we have regular characters, print them.  */
	  char *end = strchr (ptr, '%');
	  if (end != NULL)
	    result = print (stream, "%.*s", (int) (end - ptr), ptr);
	  else
	    result = print (stream, "%s", ptr);
	  ptr += result;
	}
      else if (ptr[1] == '%')
	{
	  print (stream, "%%");
	  result = 1;
	  ptr += 2;
	}
      else
	{
	  /* We have a format specifier!  */
	  char *sptr = specifier;
	  int wide_width = 0, short_width = 0;
	  unsigned int arg_no;

	  /* Copy the % and move forward.  */
	  *sptr++ = *ptr++;

	  /* Check for a positional parameter.  */
	  arg_no = -1u;
	  if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
	    {
	      arg_no = *ptr - '1';
	      ptr += 2;
	    }

	  /* Move past flags.  */
	  while (strchr ("-+ #0'I", *ptr))
	    *sptr++ = *ptr++;

	  if (*ptr == '*')
	    {
	      int value;
	      unsigned int arg_index;

	      ptr++;
	      arg_index = arg_count;
	      if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
		{
		  arg_index = *ptr - '1';
		  ptr += 2;
		}
	      value = abs (args[arg_index].i);
	      arg_count++;
	      sptr += sprintf (sptr, "%d", value);
	    }
	  else
	    /* Handle explicit numeric value.  */
	    while (ISDIGIT (*ptr))
	      *sptr++ = *ptr++;

	  /* Precision.  */
	  if (*ptr == '.')
	    {
	      /* Copy and go past the period.  */
	      *sptr++ = *ptr++;
	      if (*ptr == '*')
		{
		  int value;
		  unsigned int arg_index;

		  ptr++;
		  arg_index = arg_count;
		  if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
		    {
		      arg_index = *ptr - '1';
		      ptr += 2;
		    }
		  value = abs (args[arg_index].i);
		  arg_count++;
		  sptr += sprintf (sptr, "%d", value);
		}
	      else
		/* Handle explicit numeric value.  */
		while (ISDIGIT (*ptr))
		  *sptr++ = *ptr++;
	    }
	  while (strchr ("hlL", *ptr))
	    {
	      switch (*ptr)
		{
		case 'h':
		  short_width = 1;
		  break;
		case 'l':
		  wide_width++;
		  break;
		case 'L':
		  wide_width = 2;
		  break;
		default:
		  abort();
		}
	      *sptr++ = *ptr++;
	    }

	  /* Copy the type specifier, and NULL terminate.  */
	  *sptr++ = *ptr++;
	  *sptr = '\0';
	  if ((int) arg_no < 0)
	    arg_no = arg_count;

	  switch (ptr[-1])
	    {
	    case 'd':
	    case 'i':
	    case 'o':
	    case 'u':
	    case 'x':
	    case 'X':
	    case 'c':
	      {
		/* Short values are promoted to int, so just copy it
		   as an int and trust the C library printf to cast it
		   to the right width.  */
		if (short_width)
		  PRINT_TYPE (int, i);
		else
		  {
		    switch (wide_width)
		      {
		      case 0:
			PRINT_TYPE (int, i);
			break;
		      case 1:
			PRINT_TYPE (long, l);
			break;
		      case 2:
		      default:
#if defined (__MSVCRT__)
			sptr[-3] = 'I';
			sptr[-2] = '6';
			sptr[-1] = '4';
			*sptr++ = ptr[-1];
			*sptr = '\0';
#endif
			PRINT_TYPE (long long, ll);
			break;
		      }
		  }
	      }
	      break;
	    case 'f':
	    case 'e':
	    case 'E':
	    case 'g':
	    case 'G':
	      {
		if (wide_width == 0)
		  PRINT_TYPE (double, d);
		else
		  PRINT_TYPE (long double, ld);
	      }
	      break;
	    case 's':
	      PRINT_TYPE (char *, p);
	      break;
	    case 'p':
	      if (*ptr == 'A')
		{
		  asection *sec;
		  bfd *abfd;
		  const char *group = NULL;
		  struct coff_comdat_info *ci;

		  ptr++;
		  sec = (asection *) args[arg_no].p;
		  if (sec == NULL)
		    /* Invoking %pA with a null section pointer is an
		       internal error.  */
		    abort ();
		  abfd = sec->owner;
		  if (abfd != NULL
		      && bfd_get_flavour (abfd) == bfd_target_elf_flavour
		      && elf_next_in_group (sec) != NULL
		      && (sec->flags & SEC_GROUP) == 0)
		    group = elf_group_name (sec);
		  else if (abfd != NULL
			   && bfd_get_flavour (abfd) == bfd_target_coff_flavour
			   && (ci = bfd_coff_get_comdat_section (sec->owner,
								 sec)) != NULL)
		    group = ci->name;
		  if (group != NULL)
		    result = print (stream, "%s[%s]", sec->name, group);
		  else
		    result = print (stream, "%s", sec->name);
		}
	      else if (*ptr == 'B')
		{
		  bfd *abfd;

		  ptr++;
		  abfd = (bfd *) args[arg_no].p;
		  if (abfd == NULL)
		    /* Invoking %pB with a null bfd pointer is an
		       internal error.  */
		    abort ();
		  else if (abfd->my_archive
			   && !bfd_is_thin_archive (abfd->my_archive))
		    result = print (stream, "%s(%s)",
				    bfd_get_filename (abfd->my_archive),
				    bfd_get_filename (abfd));
		  else
		    result = print (stream, "%s", bfd_get_filename (abfd));
		}
	      else
		PRINT_TYPE (void *, p);
	      break;
	    default:
	      abort();
	    }
	  arg_count++;
	}
      if (result == -1)
	return -1;
      total_printed += result;
    }

  return total_printed;
}

/* First pass over FORMAT to gather ARGS.  Returns number of args.  */

static unsigned int
_bfd_doprnt_scan (const char *format, va_list ap, union _bfd_doprnt_args *args)
{
  const char *ptr = format;
  unsigned int arg_count = 0;

  for (unsigned int i = 0; i < MAX_ARGS; i++)
    args[i].type = Bad;

  while (*ptr != '\0')
    {
      if (*ptr != '%')
	{
	  ptr = strchr (ptr, '%');
	  if (ptr == NULL)
	    break;
	}
      else if (ptr[1] == '%')
	ptr += 2;
      else
	{
	  int wide_width = 0, short_width = 0;
	  unsigned int arg_no;
	  int arg_type;

	  ptr++;

	  /* Check for a positional parameter.  */
	  arg_no = -1u;
	  if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
	    {
	      arg_no = *ptr - '1';
	      ptr += 2;
	    }

	  /* Move past flags.  */
	  while (strchr ("-+ #0'I", *ptr))
	    ptr++;

	  if (*ptr == '*')
	    {
	      unsigned int arg_index;

	      ptr++;
	      arg_index = arg_count;
	      if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
		{
		  arg_index = *ptr - '1';
		  ptr += 2;
		}
	      if (arg_index >= MAX_ARGS)
		abort ();
	      args[arg_index].type = Int;
	      arg_count++;
	    }
	  else
	    /* Handle explicit numeric value.  */
	    while (ISDIGIT (*ptr))
	      ptr++;

	  /* Precision.  */
	  if (*ptr == '.')
	    {
	      ptr++;
	      if (*ptr == '*')
		{
		  unsigned int arg_index;

		  ptr++;
		  arg_index = arg_count;
		  if (*ptr != '0' && ISDIGIT (*ptr) && ptr[1] == '$')
		    {
		      arg_index = *ptr - '1';
		      ptr += 2;
		    }
		  if (arg_index >= MAX_ARGS)
		    abort ();
		  args[arg_index].type = Int;
		  arg_count++;
		}
	      else
		/* Handle explicit numeric value.  */
		while (ISDIGIT (*ptr))
		  ptr++;
	    }
	  while (strchr ("hlL", *ptr))
	    {
	      switch (*ptr)
		{
		case 'h':
		  short_width = 1;
		  break;
		case 'l':
		  wide_width++;
		  break;
		case 'L':
		  wide_width = 2;
		  break;
		default:
		  abort();
		}
	      ptr++;
	    }

	  ptr++;
	  if ((int) arg_no < 0)
	    arg_no = arg_count;

	  arg_type = Bad;
	  switch (ptr[-1])
	    {
	    case 'd':
	    case 'i':
	    case 'o':
	    case 'u':
	    case 'x':
	    case 'X':
	    case 'c':
	      {
		if (short_width)
		  arg_type = Int;
		else
		  {
		    switch (wide_width)
		      {
		      case 0:
			arg_type = Int;
			break;
		      case 1:
			arg_type = Long;
			break;
		      case 2:
		      default:
			arg_type = LongLong;
			break;
		      }
		  }
	      }
	      break;
	    case 'f':
	    case 'e':
	    case 'E':
	    case 'g':
	    case 'G':
	      {
		if (wide_width == 0)
		  arg_type = Double;
		else
		  arg_type = LongDouble;
	      }
	      break;
	    case 's':
	      arg_type = Ptr;
	      break;
	    case 'p':
	      if (*ptr == 'A' || *ptr == 'B')
		ptr++;
	      arg_type = Ptr;
	      break;
	    default:
	      abort();
	    }

	  if (arg_no >= MAX_ARGS)
	    abort ();
	  args[arg_no].type = arg_type;
	  arg_count++;
	}
    }

  for (unsigned int i = 0; i < arg_count; i++)
    {
      switch (args[i].type)
	{
	case Int:
	  args[i].i = va_arg (ap, int);
	  break;
	case Long:
	  args[i].l = va_arg (ap, long);
	  break;
	case LongLong:
	  args[i].ll = va_arg (ap, long long);
	  break;
	case Double:
	  args[i].d = va_arg (ap, double);
	  break;
	case LongDouble:
	  args[i].ld = va_arg (ap, long double);
	  break;
	case Ptr:
	  args[i].p = va_arg (ap, void *);
	  break;
	default:
	  abort ();
	}
    }

  return arg_count;
}

static void
_bfd_print (bfd_print_callback print_func, void *stream,
	    const char *fmt, va_list ap)
{
  union _bfd_doprnt_args args[MAX_ARGS];

  _bfd_doprnt_scan (fmt, ap, args);
  _bfd_doprnt (print_func, stream, fmt, args);
}

/*
FUNCTION
	bfd_print_error

SYNOPSIS
	void bfd_print_error (bfd_print_callback print_func,
	  void *stream, const char *fmt, va_list ap);

DESCRIPTION

	This formats FMT and AP according to BFD "printf" rules,
	sending the output to STREAM by repeated calls to PRINT_FUNC.
	PRINT_FUNC is a printf-like function; it does not need to
	implement the BFD printf format extensions.  This can be used
	in a callback that is set via bfd_set_error_handler to turn
	the error into ordinary output.
*/

void
bfd_print_error (bfd_print_callback print_func, void *stream,
		 const char *fmt, va_list ap)
{
  print_func (stream, "%s: ", _bfd_get_error_program_name ());
  _bfd_print (print_func, stream, fmt, ap);
}

/* The standard error handler that prints to stderr.  */

static void
error_handler_fprintf (const char *fmt, va_list ap)
{
  /* PR 4992: Don't interrupt output being sent to stdout.  */
  fflush (stdout);

  bfd_print_error ((bfd_print_callback) fprintf, stderr, fmt, ap);

  /* On AIX, putc is implemented as a macro that triggers a -Wunused-value
     warning, so use the fputc function to avoid it.  */
  fputc ('\n', stderr);
  fflush (stderr);
}

/* Control printing to a string buffer.  */
struct buf_stream
{
  char *ptr;
  int left;
};

/* An fprintf like function that instead prints to a string buffer.  */

static int
err_sprintf (void *stream, const char *fmt, ...)
{
  struct buf_stream *s = stream;
  va_list ap;

  va_start (ap, fmt);
  int total = vsnprintf (s->ptr, s->left, fmt, ap);
  va_end (ap);
  if (total < 0)
    ;
  else if (total > s->left)
    {
      s->ptr += s->left;
      s->left = 0;
    }
  else
    {
      s->ptr += total;
      s->left -= total;
    }
  return total;
}

/*
INTERNAL
.{* Cached _bfd_check_format messages are put in this.  *}
.struct per_xvec_message
.{
.  struct per_xvec_message *next;
.  char message[];
.};
.
.{* A list of per_xvec_message objects.  The targ field indicates
.   which xvec this list holds; PER_XVEC_NO_TARGET is only set for the
.   root of the list and indicates that the entry isn't yet used.  The
.   abfd field is only needed in the root entry of the list.  *}
.struct per_xvec_messages
.{
.  bfd *abfd;
.  const bfd_target *targ;
.  struct per_xvec_message *messages;
.  struct per_xvec_messages *next;
.};
.
.#define PER_XVEC_NO_TARGET ((const bfd_target *) -1)
*/

/* Helper function to find or allocate the correct per-xvec object
   when emitting a message.  */

static struct per_xvec_message *
_bfd_per_xvec_warn (struct per_xvec_messages *messages, size_t alloc)
{
  const bfd_target *targ = messages->abfd->xvec;

  struct per_xvec_messages *prev = NULL;
  struct per_xvec_messages *iter = messages;

  if (iter->targ == PER_XVEC_NO_TARGET)
    iter->targ = targ;
  else
    for (; iter != NULL; iter = iter->next)
      {
	if (iter->targ == targ)
	  break;
	prev = iter;
      }

  if (iter == NULL)
    {
      iter = bfd_malloc (sizeof (*iter));
      if (iter == NULL)
	return NULL;
      iter->abfd = messages->abfd;
      iter->targ = targ;
      iter->messages = NULL;
      iter->next = NULL;
      prev->next = iter;
    }

  struct per_xvec_message **m = &iter->messages;
  int count = 0;
  while (*m)
    {
      m = &(*m)->next;
      count++;
    }
  /* Anti-fuzzer measure.  Don't cache more than 5 messages.  */
  if (count < 5)
    {
      *m = bfd_malloc (sizeof (**m) + alloc);
      if (*m != NULL)
	(*m)->next = NULL;
    }
  return *m;
}

/* Communicate the error-message container processed by
   bfd_check_format_matches to the error handling function
   error_handler_sprintf.  When non-NULL, _bfd_error_handler will call
   error_handler_sprintf; when NULL, _bfd_error_internal will be used
   instead.  */

static TLS struct per_xvec_messages *error_handler_messages;

/* A special value for error_handler_messages that indicates that the
   error should simply be ignored.  */
#define IGNORE_ERROR_MESSAGES ((struct per_xvec_messages *) -1)

/* An error handler that prints to a string, then dups that string to
   a per-xvec cache.  */

static void
error_handler_sprintf (const char *fmt, va_list ap)
{
  char error_buf[1024];
  struct buf_stream error_stream;

  error_stream.ptr = error_buf;
  error_stream.left = sizeof (error_buf);

  _bfd_print (err_sprintf, &error_stream, fmt, ap);

  size_t len = error_stream.ptr - error_buf;
  struct per_xvec_message *warn
    = _bfd_per_xvec_warn (error_handler_messages, len + 1);
  if (warn)
    {
      memcpy (warn->message, error_buf, len);
      warn->message[len] = 0;
    }
}

/* This is a function pointer to the routine which should handle BFD
   error messages.  It is called when a BFD routine encounters an
   error for which it wants to print a message.  Going through a
   function pointer permits a program linked against BFD to intercept
   the messages and deal with them itself.  */

static bfd_error_handler_type _bfd_error_internal = error_handler_fprintf;

/*
FUNCTION
	_bfd_error_handler

SYNOPSIS
	void _bfd_error_handler (const char *fmt, ...) ATTRIBUTE_PRINTF_1;

DESCRIPTION
	This is the default routine to handle BFD error messages.
	Like fprintf (stderr, ...), but also handles some extra format
	specifiers.

	%pA section name from section.  For group components, prints
	group name too.
	%pB file name from bfd.  For archive components, prints
	archive too.

	Beware: Only supports a maximum of 9 format arguments.
*/

void
_bfd_error_handler (const char *fmt, ...)
{
  va_list ap;

  va_start (ap, fmt);
  if (error_handler_messages == IGNORE_ERROR_MESSAGES)
    {
      /* Nothing.  */
    }
  else if (error_handler_messages != NULL)
    error_handler_sprintf (fmt, ap);
  else
    _bfd_error_internal (fmt, ap);
  va_end (ap);
}

/*
FUNCTION
	bfd_set_error_handler

SYNOPSIS
	bfd_error_handler_type bfd_set_error_handler (bfd_error_handler_type);

DESCRIPTION
	Set the BFD error handler function.  Returns the previous
	function.
*/

bfd_error_handler_type
bfd_set_error_handler (bfd_error_handler_type pnew)
{
  bfd_error_handler_type pold;

  pold = _bfd_error_internal;
  _bfd_error_internal = pnew;
  return pold;
}

/*
INTERNAL_FUNCTION
	_bfd_set_error_handler_caching

SYNOPSIS
	struct per_xvec_messages *_bfd_set_error_handler_caching (struct per_xvec_messages *);

DESCRIPTION
	Set the BFD error handler function to one that stores messages
	to the per_xvec_messages object.  Returns the previous object
	to which messages are stored.  Note that two sequential calls
	to this with a non-NULL argument will cause output to be
	dropped, rather than gathered.
*/

struct per_xvec_messages *
_bfd_set_error_handler_caching (struct per_xvec_messages *messages)
{
  struct per_xvec_messages *old = error_handler_messages;
  if (old == NULL)
    error_handler_messages = messages;
  else
    error_handler_messages = IGNORE_ERROR_MESSAGES;
  return old;
}

/*
INTERNAL_FUNCTION
	_bfd_restore_error_handler_caching

SYNOPSIS
	void _bfd_restore_error_handler_caching (struct per_xvec_messages *);

DESCRIPTION
	Reset the BFD error handler object to an earlier value.
*/

void
_bfd_restore_error_handler_caching (struct per_xvec_messages *old)
{
  error_handler_messages = old;
}

/*
FUNCTION
	bfd_set_error_program_name

SYNOPSIS
	void bfd_set_error_program_name (const char *);

DESCRIPTION
	Set the program name to use when printing a BFD error.  This
	is printed before the error message followed by a colon and
	space.  The string must not be changed after it is passed to
	this function.
*/

void
bfd_set_error_program_name (const char *name)
{
  _bfd_error_program_name = name;
}

/*
INTERNAL_FUNCTION
	_bfd_get_error_program_name

SYNOPSIS
	const char *_bfd_get_error_program_name (void);

DESCRIPTION
	Get the program name used when printing a BFD error.
*/

const char *
_bfd_get_error_program_name (void)
{
  if (_bfd_error_program_name != NULL)
    return _bfd_error_program_name;
  return "BFD";
}

/*
SUBSECTION
	BFD assert handler

	If BFD finds an internal inconsistency, the bfd assert
	handler is called with information on the BFD version, BFD
	source file and line.  If this happens, most programs linked
	against BFD are expected to want to exit with an error, or mark
	the current BFD operation as failed, so it is recommended to
	override the default handler, which just calls
	_bfd_error_handler and continues.

CODE_FRAGMENT
.typedef void (*bfd_assert_handler_type) (const char *bfd_formatmsg,
.					  const char *bfd_version,
.					  const char *bfd_file,
.					  int bfd_line);
.
*/

/* Note the use of bfd_ prefix on the parameter names above: we want to
   show which one is the message and which is the version by naming the
   parameters, but avoid polluting the program-using-bfd namespace as
   the typedef is visible in the exported headers that the program
   includes.  Below, it's just for consistency.  */

static void
_bfd_default_assert_handler (const char *bfd_formatmsg,
			     const char *bfd_version,
			     const char *bfd_file,
			     int bfd_line)

{
  _bfd_error_handler (bfd_formatmsg, bfd_version, bfd_file, bfd_line);
}

/* Similar to _bfd_error_handler, a program can decide to exit on an
   internal BFD error.  We use a non-variadic type to simplify passing
   on parameters to other functions, e.g. _bfd_error_handler.  */

static bfd_assert_handler_type _bfd_assert_handler = _bfd_default_assert_handler;

/*
FUNCTION
	bfd_set_assert_handler

SYNOPSIS
	bfd_assert_handler_type bfd_set_assert_handler (bfd_assert_handler_type);

DESCRIPTION
	Set the BFD assert handler function.  Returns the previous
	function.
*/

bfd_assert_handler_type
bfd_set_assert_handler (bfd_assert_handler_type pnew)
{
  bfd_assert_handler_type pold;

  pold = _bfd_assert_handler;
  _bfd_assert_handler = pnew;
  return pold;
}

/*
INODE
Initialization, Threading, Error reporting, BFD front end

FUNCTION
	bfd_init

SYNOPSIS
	unsigned int bfd_init (void);

DESCRIPTION
	This routine must be called before any other BFD function to
	initialize magical internal data structures.
	Returns a magic number, which may be used to check
	that the bfd library is configured as expected by users.

.{* Value returned by bfd_init.  *}
.#define BFD_INIT_MAGIC (sizeof (struct bfd_section))
.
*/

unsigned int
bfd_init (void)
{
  bfd_error = bfd_error_no_error;
  input_bfd = NULL;
  _bfd_clear_error_data ();
  input_error = bfd_error_no_error;
  _bfd_error_internal = error_handler_fprintf;
  _bfd_assert_handler = _bfd_default_assert_handler;

  return BFD_INIT_MAGIC;
}


/*
INODE
Threading, Miscellaneous, Initialization, BFD front end

SECTION
	Threading

	BFD has limited support for thread-safety.  Most BFD globals
	are protected by locks, while the error-related globals are
	thread-local.  A given BFD cannot safely be used from two
	threads at the same time; it is up to the application to do
	any needed locking.  However, it is ok for different threads
	to work on different BFD objects at the same time.

SUBSECTION
	Thread functions.

CODE_FRAGMENT
.typedef bool (*bfd_lock_unlock_fn_type) (void *);
*/

/* The lock and unlock functions, if set.  */
static bfd_lock_unlock_fn_type lock_fn;
static bfd_lock_unlock_fn_type unlock_fn;
static void *lock_data;

/*
FUNCTION
	bfd_thread_init

SYNOPSIS
	bool bfd_thread_init
	  (bfd_lock_unlock_fn_type lock,
	  bfd_lock_unlock_fn_type unlock,
	  void *data);

DESCRIPTION

	Initialize BFD threading.  The functions passed in will be
	used to lock and unlock global data structures.  This may only
	be called a single time in a given process.  Returns true on
	success and false on error.  DATA is passed verbatim to the
	lock and unlock functions.  The lock and unlock functions
	should return true on success, or set the BFD error and return
	false on failure.
*/

bool
bfd_thread_init (bfd_lock_unlock_fn_type lock, bfd_lock_unlock_fn_type unlock,
		 void *data)
{
  /* Both functions must be set, and this cannot have been called
     before.  */
  if (lock == NULL || unlock == NULL || unlock_fn != NULL)
    {
      bfd_set_error (bfd_error_invalid_operation);
      return false;
    }

  lock_fn = lock;
  unlock_fn = unlock;
  lock_data = data;
  return true;
}

/*
FUNCTION
	bfd_thread_cleanup

SYNOPSIS
	void bfd_thread_cleanup (void);

DESCRIPTION
	Clean up any thread-local state.  This should be called by a
	thread that uses any BFD functions, before the thread exits.
	It is fine to call this multiple times, or to call it and then
	later call BFD functions on the same thread again.
*/

void
bfd_thread_cleanup (void)
{
  _bfd_clear_error_data ();
}

/*
INTERNAL_FUNCTION
	bfd_lock

SYNOPSIS
	bool bfd_lock (void);

DESCRIPTION
	Acquire the global BFD lock, if needed.  Returns true on
	success, false on error.
*/

bool
bfd_lock (void)
{
  if (lock_fn != NULL)
    return lock_fn (lock_data);
  return true;
}

/*
INTERNAL_FUNCTION
	bfd_unlock

SYNOPSIS
	bool bfd_unlock (void);

DESCRIPTION
	Release the global BFD lock, if needed.  Returns true on
	success, false on error.
*/

bool
bfd_unlock (void)
{
  if (unlock_fn != NULL)
    return unlock_fn (lock_data);
  return true;
}


/*
INODE
Miscellaneous, Memory Usage, Threading, BFD front end

SECTION
	Miscellaneous

SUBSECTION
	Miscellaneous functions
*/

/*
FUNCTION
	bfd_get_reloc_upper_bound

SYNOPSIS
	long bfd_get_reloc_upper_bound (bfd *abfd, asection *sect);

DESCRIPTION
	Return the number of bytes required to store the
	relocation information associated with section @var{sect}
	attached to bfd @var{abfd}.  If an error occurs, return -1.

*/

long
bfd_get_reloc_upper_bound (bfd *abfd, sec_ptr asect)
{
  if (abfd->format != bfd_object)
    {
      bfd_set_error (bfd_error_invalid_operation);
      return -1;
    }

  return BFD_SEND (abfd, _get_reloc_upper_bound, (abfd, asect));
}

/*
FUNCTION
	bfd_canonicalize_reloc

SYNOPSIS
	long bfd_canonicalize_reloc
	  (bfd *abfd, asection *sec, arelent **loc, asymbol **syms);

DESCRIPTION
	Call the back end associated with the open BFD
	@var{abfd} and translate the external form of the relocation
	information attached to @var{sec} into the internal canonical
	form.  Place the table into memory at @var{loc}, which has
	been preallocated, usually by a call to
	<<bfd_get_reloc_upper_bound>>.  Returns the number of relocs, or
	-1 on error.

	The @var{syms} table is also needed for horrible internal magic
	reasons.

*/
long
bfd_canonicalize_reloc (bfd *abfd,
			sec_ptr asect,
			arelent **location,
			asymbol **symbols)
{
  if (abfd->format != bfd_object)
    {
      bfd_set_error (bfd_error_invalid_operation);
      return -1;
    }

  return BFD_SEND (abfd, _bfd_canonicalize_reloc,
		   (abfd, asect, location, symbols));
}

/*
FUNCTION
	bfd_set_reloc

SYNOPSIS
	void bfd_set_reloc
	  (bfd *abfd, asection *sec, arelent **rel, unsigned int count);

DESCRIPTION
	Set the relocation pointer and count within
	section @var{sec} to the values @var{rel} and @var{count}.
	The argument @var{abfd} is ignored.

.#define bfd_set_reloc(abfd, asect, location, count) \
.	BFD_SEND (abfd, _bfd_set_reloc, (abfd, asect, location, count))
*/

/*
FUNCTION
	bfd_set_file_flags

SYNOPSIS
	bool bfd_set_file_flags (bfd *abfd, flagword flags);

DESCRIPTION
	Set the flag word in the BFD @var{abfd} to the value @var{flags}.

	Possible errors are:
	o <<bfd_error_wrong_format>> - The target bfd was not of object format.
	o <<bfd_error_invalid_operation>> - The target bfd was open for reading.
	o <<bfd_error_invalid_operation>> -
	The flag word contained a bit which was not applicable to the
	type of file.  E.g., an attempt was made to set the <<D_PAGED>> bit
	on a BFD format which does not support demand paging.

*/

bool
bfd_set_file_flags (bfd *abfd, flagword flags)
{
  if (abfd->format != bfd_object)
    {
      bfd_set_error (bfd_error_wrong_format);
      return false;
    }

  if (bfd_read_p (abfd))
    {
      bfd_set_error (bfd_error_invalid_operation);
      return false;
    }

  abfd->flags = flags;
  if ((flags & bfd_applicable_file_flags (abfd)) != flags)
    {
      bfd_set_error (bfd_error_invalid_operation);
      return false;
    }

  return true;
}

void
bfd_assert (const char *file, int line)
{
  /* xgettext:c-format */
  (*_bfd_assert_handler) (_("BFD %s assertion fail %s:%d"),
			  BFD_VERSION_STRING, file, line);
}

/* A more or less friendly abort message.  In libbfd.h abort is
   defined to call this function.  */

void
_bfd_abort (const char *file, int line, const char *fn)
{
  fflush (stdout);

  if (fn != NULL)
    fprintf (stderr, _("%s: BFD %s internal error, aborting at %s:%d in %s\n"),
	     _bfd_get_error_program_name (), BFD_VERSION_STRING,
	     file, line, fn);
  else
    fprintf (stderr, _("%s: BFD %s internal error, aborting at %s:%d\n"),
	     _bfd_get_error_program_name (), BFD_VERSION_STRING,
	     file, line);
  fprintf (stderr, _("Please report this bug.\n"));
  _exit (EXIT_FAILURE);
}

/*
FUNCTION
	bfd_get_arch_size

SYNOPSIS
	int bfd_get_arch_size (bfd *abfd);

DESCRIPTION
	Returns the normalized architecture address size, in bits, as
	determined by the object file's format.  By normalized, we mean
	either 32 or 64.  For ELF, this information is included in the
	header.  Use bfd_arch_bits_per_address for number of bits in
	the architecture address.

	Returns the arch size in bits if known, <<-1>> otherwise.
*/

int
bfd_get_arch_size (bfd *abfd)
{
  if (abfd->xvec->flavour == bfd_target_elf_flavour)
    return get_elf_backend_data (abfd)->s->arch_size;

  return bfd_arch_bits_per_address (abfd) > 32 ? 64 : 32;
}

/*
FUNCTION
	bfd_get_sign_extend_vma

SYNOPSIS
	int bfd_get_sign_extend_vma (bfd *abfd);

DESCRIPTION
	Indicates if the target architecture "naturally" sign extends
	an address.  Some architectures implicitly sign extend address
	values when they are converted to types larger than the size
	of an address.  For instance, bfd_get_start_address() will
	return an address sign extended to fill a bfd_vma when this is
	the case.

	Returns <<1>> if the target architecture is known to sign
	extend addresses, <<0>> if the target architecture is known to
	not sign extend addresses, and <<-1>> otherwise.
*/

int
bfd_get_sign_extend_vma (bfd *abfd)
{
  const char *name;

  if (bfd_get_flavour (abfd) == bfd_target_elf_flavour)
    return get_elf_backend_data (abfd)->sign_extend_vma;

  name = bfd_get_target (abfd);

  /* Return a proper value for DJGPP & PE COFF.
     This function is required for DWARF2 support, but there is
     no place to store this information in the COFF back end.
     Should enough other COFF targets add support for DWARF2,
     a place will have to be found.  Until then, this hack will do.  */
  if (startswith (name, "coff-go32")
      || strcmp (name, "pe-i386") == 0
      || strcmp (name, "pei-i386") == 0
      || strcmp (name, "pe-x86-64") == 0
      || strcmp (name, "pei-x86-64") == 0
      || strcmp (name, "pe-aarch64-little") == 0
      || strcmp (name, "pei-aarch64-little") == 0
      || strcmp (name, "pe-arm-wince-little") == 0
      || strcmp (name, "pei-arm-wince-little") == 0
      || strcmp (name, "pei-loongarch64") == 0
      || strcmp (name, "pei-riscv64-little") == 0
      || strcmp (name, "aixcoff-rs6000") == 0
      || strcmp (name, "aix5coff64-rs6000") == 0)
    return 1;

  if (startswith (name, "mach-o"))
    return 0;

  bfd_set_error (bfd_error_wrong_format);
  return -1;
}

/*
FUNCTION
	bfd_set_start_address

SYNOPSIS
	bool bfd_set_start_address (bfd *abfd, bfd_vma vma);

DESCRIPTION
	Make @var{vma} the entry point of output BFD @var{abfd}.

	Returns <<TRUE>> on success, <<FALSE>> otherwise.
*/

bool
bfd_set_start_address (bfd *abfd, bfd_vma vma)
{
  abfd->start_address = vma;
  return true;
}

/*
FUNCTION
	bfd_get_gp_size

SYNOPSIS
	unsigned int bfd_get_gp_size (bfd *abfd);

DESCRIPTION
	Return the maximum size of objects to be optimized using the GP
	register under MIPS ECOFF.  This is typically set by the <<-G>>
	argument to the compiler, assembler or linker.
*/

unsigned int
bfd_get_gp_size (bfd *abfd)
{
  if (abfd->format == bfd_object)
    {
      if (abfd->xvec->flavour == bfd_target_ecoff_flavour)
	return ecoff_data (abfd)->gp_size;
      else if (abfd->xvec->flavour == bfd_target_elf_flavour)
	return elf_gp_size (abfd);
    }
  return 0;
}

/*
FUNCTION
	bfd_set_gp_size

SYNOPSIS
	void bfd_set_gp_size (bfd *abfd, unsigned int i);

DESCRIPTION
	Set the maximum size of objects to be optimized using the GP
	register under ECOFF or MIPS ELF.  This is typically set by
	the <<-G>> argument to the compiler, assembler or linker.
*/

void
bfd_set_gp_size (bfd *abfd, unsigned int i)
{
  /* Don't try to set GP size on an archive or core file!  */
  if (abfd->format != bfd_object)
    return;

  if (abfd->xvec->flavour == bfd_target_ecoff_flavour)
    ecoff_data (abfd)->gp_size = i;
  else if (abfd->xvec->flavour == bfd_target_elf_flavour)
    elf_gp_size (abfd) = i;
}

/* Get the GP value.  This is an internal function used by some of the
   relocation special_function routines on targets which support a GP
   register.  */

bfd_vma
_bfd_get_gp_value (bfd *abfd)
{
  if (! abfd)
    return 0;
  if (abfd->format != bfd_object)
    return 0;

  if (abfd->xvec->flavour == bfd_target_ecoff_flavour)
    return ecoff_data (abfd)->gp;
  else if (abfd->xvec->flavour == bfd_target_elf_flavour)
    return elf_gp (abfd);

  return 0;
}

/* Set the GP value.  */

void
_bfd_set_gp_value (bfd *abfd, bfd_vma v)
{
  if (! abfd)
    abort ();
  if (abfd->format != bfd_object)
    return;

  if (abfd->xvec->flavour == bfd_target_ecoff_flavour)
    ecoff_data (abfd)->gp = v;
  else if (abfd->xvec->flavour == bfd_target_elf_flavour)
    elf_gp (abfd) = v;
}

/*
FUNCTION
	bfd_set_gp_value

SYNOPSIS
	void bfd_set_gp_value (bfd *abfd, bfd_vma v);

DESCRIPTION
	Allow external access to the fucntion to set the GP value.
	This is specifically added for gdb-compile support.
*/

void
bfd_set_gp_value (bfd *abfd, bfd_vma v)
{
  _bfd_set_gp_value (abfd, v);
}

/*
FUNCTION
	bfd_scan_vma

SYNOPSIS
	bfd_vma bfd_scan_vma (const char *string, const char **end, int base);

DESCRIPTION
	Convert, like <<strtoul>> or <<stdtoull> depending on the size
	of a <<bfd_vma>>, a numerical expression @var{string} into a
	<<bfd_vma>> integer, and return that integer.
*/

bfd_vma
bfd_scan_vma (const char *string, const char **end, int base)
{
  if (sizeof (bfd_vma) <= sizeof (unsigned long))
    return strtoul (string, (char **) end, base);

  if (sizeof (bfd_vma) <= sizeof (unsigned long long))
    return strtoull (string, (char **) end, base);

  abort ();
}

/*
FUNCTION
	bfd_copy_private_header_data

SYNOPSIS
	bool bfd_copy_private_header_data (bfd *ibfd, bfd *obfd);

DESCRIPTION
	Copy private BFD header information from the BFD @var{ibfd} to the
	the BFD @var{obfd}.  This copies information that may require
	sections to exist, but does not require symbol tables.  Return
	<<true>> on success, <<false>> on error.
	Possible error returns are:

	o <<bfd_error_no_memory>> -
	Not enough memory exists to create private data for @var{obfd}.

.#define bfd_copy_private_header_data(ibfd, obfd) \
.	BFD_SEND (obfd, _bfd_copy_private_header_data, \
.		  (ibfd, obfd))

*/

/*
FUNCTION
	bfd_copy_private_bfd_data

SYNOPSIS
	bool bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd);

DESCRIPTION
	Copy private BFD information from the BFD @var{ibfd} to the
	the BFD @var{obfd}.  Return <<TRUE>> on success, <<FALSE>> on error.
	Possible error returns are:

	o <<bfd_error_no_memory>> -
	Not enough memory exists to create private data for @var{obfd}.

.#define bfd_copy_private_bfd_data(ibfd, obfd) \
.	BFD_SEND (obfd, _bfd_copy_private_bfd_data, \
.		  (ibfd, obfd))

*/

/*
FUNCTION
	bfd_set_private_flags

SYNOPSIS
	bool bfd_set_private_flags (bfd *abfd, flagword flags);

DESCRIPTION
	Set private BFD flag information in the BFD @var{abfd}.
	Return <<TRUE>> on success, <<FALSE>> on error.  Possible error
	returns are:

	o <<bfd_error_no_memory>> -
	Not enough memory exists to create private data for @var{obfd}.

.#define bfd_set_private_flags(abfd, flags) \
.	BFD_SEND (abfd, _bfd_set_private_flags, (abfd, flags))

*/

/*
FUNCTION
	Other functions

DESCRIPTION
	The following functions exist but have not yet been documented.

.#define bfd_sizeof_headers(abfd, info) \
.	BFD_SEND (abfd, _bfd_sizeof_headers, (abfd, info))
.
.#define bfd_find_nearest_line(abfd, sec, syms, off, file, func, line) \
.	BFD_SEND (abfd, _bfd_find_nearest_line, \
.		  (abfd, syms, sec, off, file, func, line, NULL))
.
.#define bfd_find_nearest_line_with_alt(abfd, alt_filename, sec, syms, off, \
.					file, func, line, disc) \
.	BFD_SEND (abfd, _bfd_find_nearest_line_with_alt, \
.		  (abfd, alt_filename, syms, sec, off, file, func, line, disc))
.
.#define bfd_find_nearest_line_discriminator(abfd, sec, syms, off, file, func, \
.					    line, disc) \
.	BFD_SEND (abfd, _bfd_find_nearest_line, \
.		  (abfd, syms, sec, off, file, func, line, disc))
.
.#define bfd_find_line(abfd, syms, sym, file, line) \
.	BFD_SEND (abfd, _bfd_find_line, \
.		  (abfd, syms, sym, file, line))
.
.#define bfd_find_inliner_info(abfd, file, func, line) \
.	BFD_SEND (abfd, _bfd_find_inliner_info, \
.		  (abfd, file, func, line))
.
.#define bfd_debug_info_start(abfd) \
.	BFD_SEND (abfd, _bfd_debug_info_start, (abfd))
.
.#define bfd_debug_info_end(abfd) \
.	BFD_SEND (abfd, _bfd_debug_info_end, (abfd))
.
.#define bfd_debug_info_accumulate(abfd, section) \
.	BFD_SEND (abfd, _bfd_debug_info_accumulate, (abfd, section))
.
.#define bfd_stat_arch_elt(abfd, stat) \
.	BFD_SEND (abfd->my_archive ? abfd->my_archive : abfd, \
.		  _bfd_stat_arch_elt, (abfd, stat))
.
.#define bfd_update_armap_timestamp(abfd) \
.	BFD_SEND (abfd, _bfd_update_armap_timestamp, (abfd))
.
.#define bfd_set_arch_mach(abfd, arch, mach)\
.	BFD_SEND ( abfd, _bfd_set_arch_mach, (abfd, arch, mach))
.
.#define bfd_relax_section(abfd, section, link_info, again) \
.	BFD_SEND (abfd, _bfd_relax_section, (abfd, section, link_info, again))
.
.#define bfd_gc_sections(abfd, link_info) \
.	BFD_SEND (abfd, _bfd_gc_sections, (abfd, link_info))
.
.#define bfd_lookup_section_flags(link_info, flag_info, section) \
.	BFD_SEND (abfd, _bfd_lookup_section_flags, (link_info, flag_info, section))
.
.#define bfd_merge_sections(abfd, link_info) \
.	BFD_SEND (abfd, _bfd_merge_sections, (abfd, link_info))
.
.#define bfd_is_group_section(abfd, sec) \
.	BFD_SEND (abfd, _bfd_is_group_section, (abfd, sec))
.
.#define bfd_group_name(abfd, sec) \
.	BFD_SEND (abfd, _bfd_group_name, (abfd, sec))
.
.#define bfd_discard_group(abfd, sec) \
.	BFD_SEND (abfd, _bfd_discard_group, (abfd, sec))
.
.#define bfd_link_hash_table_create(abfd) \
.	BFD_SEND (abfd, _bfd_link_hash_table_create, (abfd))
.
.#define bfd_link_add_symbols(abfd, info) \
.	BFD_SEND (abfd, _bfd_link_add_symbols, (abfd, info))
.
.#define bfd_link_just_syms(abfd, sec, info) \
.	BFD_SEND (abfd, _bfd_link_just_syms, (sec, info))
.
.#define bfd_final_link(abfd, info) \
.	BFD_SEND (abfd, _bfd_final_link, (abfd, info))
.
.#define bfd_free_cached_info(abfd) \
.	BFD_SEND (abfd, _bfd_free_cached_info, (abfd))
.
.#define bfd_get_dynamic_symtab_upper_bound(abfd) \
.	BFD_SEND (abfd, _bfd_get_dynamic_symtab_upper_bound, (abfd))
.
.#define bfd_print_private_bfd_data(abfd, file)\
.	BFD_SEND (abfd, _bfd_print_private_bfd_data, (abfd, file))
.
.#define bfd_canonicalize_dynamic_symtab(abfd, asymbols) \
.	BFD_SEND (abfd, _bfd_canonicalize_dynamic_symtab, (abfd, asymbols))
.
.#define bfd_get_synthetic_symtab(abfd, count, syms, dyncount, dynsyms, ret) \
.	BFD_SEND (abfd, _bfd_get_synthetic_symtab, (abfd, count, syms, \
.						    dyncount, dynsyms, ret))
.
.#define bfd_get_dynamic_reloc_upper_bound(abfd) \
.	BFD_SEND (abfd, _bfd_get_dynamic_reloc_upper_bound, (abfd))
.
.#define bfd_canonicalize_dynamic_reloc(abfd, arels, asyms) \
.	BFD_SEND (abfd, _bfd_canonicalize_dynamic_reloc, (abfd, arels, asyms))
.
*/

/*
FUNCTION
	bfd_get_relocated_section_contents

SYNOPSIS
	bfd_byte *bfd_get_relocated_section_contents
	  (bfd *, struct bfd_link_info *, struct bfd_link_order *, bfd_byte *,
	   bool, asymbol **);

DESCRIPTION
	Read and relocate the indirect link_order section, into DATA
	(if non-NULL) or to a malloc'd buffer.  Return the buffer, or
	NULL on errors.
*/

bfd_byte *
bfd_get_relocated_section_contents (bfd *abfd,
				    struct bfd_link_info *link_info,
				    struct bfd_link_order *link_order,
				    bfd_byte *data,
				    bool relocatable,
				    asymbol **symbols)
{
  bfd *abfd2;
  bfd_byte *(*fn) (bfd *, struct bfd_link_info *, struct bfd_link_order *,
		   bfd_byte *, bool, asymbol **);

  if (link_order->type == bfd_indirect_link_order)
    {
      abfd2 = link_order->u.indirect.section->owner;
      if (abfd2 == NULL)
	abfd2 = abfd;
    }
  else
    abfd2 = abfd;

  fn = abfd2->xvec->_bfd_get_relocated_section_contents;

  return (*fn) (abfd, link_info, link_order, data, relocatable, symbols);
}

/*
FUNCTION
	bfd_record_phdr

SYNOPSIS
	bool bfd_record_phdr
	  (bfd *, unsigned long, bool, flagword, bool, bfd_vma,
	   bool, bool, unsigned int, struct bfd_section **);

DESCRIPTION
	Record information about an ELF program header.
*/

bool
bfd_record_phdr (bfd *abfd,
		 unsigned long type,
		 bool flags_valid,
		 flagword flags,
		 bool at_valid,
		 bfd_vma at,  /* Bytes.  */
		 bool includes_filehdr,
		 bool includes_phdrs,
		 unsigned int count,
		 asection **secs)
{
  struct elf_segment_map *m, **pm;
  size_t amt;
  unsigned int opb = bfd_octets_per_byte (abfd, NULL);

  if (bfd_get_flavour (abfd) != bfd_target_elf_flavour)
    return true;

  amt = sizeof (struct elf_segment_map);
  amt += ((bfd_size_type) count - 1) * sizeof (asection *);
  m = (struct elf_segment_map *) bfd_zalloc (abfd, amt);
  if (m == NULL)
    return false;

  m->p_type = type;
  m->p_flags = flags;
  m->p_paddr = at * opb;
  m->p_flags_valid = flags_valid;
  m->p_paddr_valid = at_valid;
  m->includes_filehdr = includes_filehdr;
  m->includes_phdrs = includes_phdrs;
  m->count = count;
  if (count > 0)
    memcpy (m->sections, secs, count * sizeof (asection *));

  for (pm = &elf_seg_map (abfd); *pm != NULL; pm = &(*pm)->next)
    ;
  *pm = m;

  return true;
}

#ifdef BFD64
/* Return true iff this target is 32-bit.  */

static bool
is32bit (bfd *abfd)
{
  if (bfd_get_flavour (abfd) == bfd_target_elf_flavour)
    {
      const struct elf_backend_data *bed = get_elf_backend_data (abfd);
      return bed->s->elfclass == ELFCLASS32;
    }

  /* For non-ELF targets, use architecture information.  */
  return bfd_arch_bits_per_address (abfd) <= 32;
}
#endif

/*
FUNCTION
	bfd_sprintf_vma
	bfd_fprintf_vma

SYNOPSIS
	void bfd_sprintf_vma (bfd *, char *, bfd_vma);
	void bfd_fprintf_vma (bfd *, void *, bfd_vma);

DESCRIPTION
	bfd_sprintf_vma and bfd_fprintf_vma display an address in the
	target's address size.

EXTERNAL
.#define bfd_printf_vma(abfd,x) bfd_fprintf_vma (abfd, stdout, x)
.
*/

void
bfd_sprintf_vma (bfd *abfd ATTRIBUTE_UNUSED, char *buf, bfd_vma value)
{
#ifdef BFD64
  if (!is32bit (abfd))
    {
      sprintf (buf, "%016" PRIx64, (uint64_t) value);
      return;
    }
#endif
  sprintf (buf, "%08lx", (unsigned long) value & 0xffffffff);
}

void
bfd_fprintf_vma (bfd *abfd ATTRIBUTE_UNUSED, void *stream, bfd_vma value)
{
#ifdef BFD64
  if (!is32bit (abfd))
    {
      fprintf ((FILE *) stream, "%016" PRIx64, (uint64_t) value);
      return;
    }
#endif
  fprintf ((FILE *) stream, "%08lx", (unsigned long) value & 0xffffffff);
}

/*
FUNCTION
	bfd_alt_mach_code

SYNOPSIS
	bool bfd_alt_mach_code (bfd *abfd, int alternative);

DESCRIPTION

	When more than one machine code number is available for the
	same machine type, this function can be used to switch between
	the preferred one (alternative == 0) and any others.  Currently,
	only ELF supports this feature, with up to two alternate
	machine codes.
*/

bool
bfd_alt_mach_code (bfd *abfd, int alternative)
{
  if (bfd_get_flavour (abfd) == bfd_target_elf_flavour)
    {
      int code;

      switch (alternative)
	{
	case 0:
	  code = get_elf_backend_data (abfd)->elf_machine_code;
	  break;

	case 1:
	  code = get_elf_backend_data (abfd)->elf_machine_alt1;
	  if (code == 0)
	    return false;
	  break;

	case 2:
	  code = get_elf_backend_data (abfd)->elf_machine_alt2;
	  if (code == 0)
	    return false;
	  break;

	default:
	  return false;
	}

      elf_elfheader (abfd)->e_machine = code;

      return true;
    }

  return false;
}

/*
FUNCTION
	bfd_emul_get_maxpagesize

SYNOPSIS
	bfd_vma bfd_emul_get_maxpagesize (const char *);

DESCRIPTION
	Returns the maximum page size, in bytes, as determined by
	emulation.
*/

bfd_vma
bfd_emul_get_maxpagesize (const char *emul)
{
  const bfd_target *target;

  target = bfd_find_target (emul, NULL);
  if (target != NULL
      && target->flavour == bfd_target_elf_flavour)
    return xvec_get_elf_backend_data (target)->maxpagesize;

  return 0;
}

/*
FUNCTION
	bfd_emul_get_commonpagesize

SYNOPSIS
	bfd_vma bfd_emul_get_commonpagesize (const char *);

DESCRIPTION
	Returns the common page size, in bytes, as determined by
	emulation.
*/

bfd_vma
bfd_emul_get_commonpagesize (const char *emul)
{
  const bfd_target *target;

  target = bfd_find_target (emul, NULL);
  if (target != NULL
      && target->flavour == bfd_target_elf_flavour)
    {
      const struct elf_backend_data *bed;

      bed = xvec_get_elf_backend_data (target);
      return bed->commonpagesize;
    }
  return 0;
}

/*
FUNCTION
	bfd_demangle

SYNOPSIS
	char *bfd_demangle (bfd *, const char *, int);

DESCRIPTION
	Wrapper around cplus_demangle.  Strips leading underscores and
	other such chars that would otherwise confuse the demangler.
	If passed a g++ v3 ABI mangled name, returns a buffer allocated
	with malloc holding the demangled name.  Returns NULL otherwise
	and on memory alloc failure.
*/

char *
bfd_demangle (bfd *abfd, const char *name, int options)
{
  char *res, *alloc;
  const char *pre, *suf;
  size_t pre_len;
  bool skip_lead;

  skip_lead = (abfd != NULL
	       && *name != '\0'
	       && bfd_get_symbol_leading_char (abfd) == *name);
  if (skip_lead)
    ++name;

  /* This is a hack for better error reporting on XCOFF, PowerPC64-ELF
     or the MS PE format.  These formats have a number of leading '.'s
     on at least some symbols, so we remove all dots to avoid
     confusing the demangler.  */
  pre = name;
  while (*name == '.' || *name == '$')
    ++name;
  pre_len = name - pre;

  /* Strip off @plt and suchlike too.  */
  alloc = NULL;
  suf = strchr (name, '@');
  if (suf != NULL)
    {
      alloc = (char *) bfd_malloc (suf - name + 1);
      if (alloc == NULL)
	return NULL;
      memcpy (alloc, name, suf - name);
      alloc[suf - name] = '\0';
      name = alloc;
    }

  res = cplus_demangle (name, options);

  free (alloc);

  if (res == NULL)
    {
      if (skip_lead)
	{
	  size_t len = strlen (pre) + 1;
	  alloc = (char *) bfd_malloc (len);
	  if (alloc == NULL)
	    return NULL;
	  memcpy (alloc, pre, len);
	  return alloc;
	}
      return NULL;
    }

  /* Put back any prefix or suffix.  */
  if (pre_len != 0 || suf != NULL)
    {
      size_t len;
      size_t suf_len;
      char *final;

      len = strlen (res);
      if (suf == NULL)
	suf = res + len;
      suf_len = strlen (suf) + 1;
      final = (char *) bfd_malloc (pre_len + len + suf_len);
      if (final != NULL)
	{
	  memcpy (final, pre, pre_len);
	  memcpy (final + pre_len, res, len);
	  memcpy (final + pre_len + len, suf, suf_len);
	}
      free (res);
      res = final;
    }

  return res;
}

/* Get the linker information.  */

struct bfd_link_info *
_bfd_get_link_info (bfd *abfd)
{
  if (bfd_get_flavour (abfd) != bfd_target_elf_flavour)
    return NULL;

  return elf_link_info (abfd);
}
