OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-6.8/] [bfd/] [archive.c] - Diff between revs 157 and 225

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 157 Rev 225
Line 1... Line 1...
/* BFD back-end for archive files (libraries).
/* BFD back-end for archive files (libraries).
   Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
   Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
   Free Software Foundation, Inc.
   Free Software Foundation, Inc.
   Written by Cygnus Support.  Mostly Gumby Henkel-Wallace's fault.
   Written by Cygnus Support.  Mostly Gumby Henkel-Wallace's fault.
 
 
   This file is part of BFD, the Binary File Descriptor library.
   This file is part of BFD, the Binary File Descriptor library.
 
 
Line 135... Line 135...
#include "libbfd.h"
#include "libbfd.h"
#include "aout/ar.h"
#include "aout/ar.h"
#include "aout/ranlib.h"
#include "aout/ranlib.h"
#include "safe-ctype.h"
#include "safe-ctype.h"
#include "hashtab.h"
#include "hashtab.h"
 
#include "filenames.h"
 
 
#ifndef errno
#ifndef errno
extern int errno;
extern int errno;
#endif
#endif
 
 
Line 178... Line 179...
bfd_boolean
bfd_boolean
_bfd_generic_mkarchive (bfd *abfd)
_bfd_generic_mkarchive (bfd *abfd)
{
{
  bfd_size_type amt = sizeof (struct artdata);
  bfd_size_type amt = sizeof (struct artdata);
 
 
  abfd->tdata.aout_ar_data = bfd_zalloc (abfd, amt);
  abfd->tdata.aout_ar_data = (struct artdata *) bfd_zalloc (abfd, amt);
  if (bfd_ardata (abfd) == NULL)
  if (bfd_ardata (abfd) == NULL)
    return FALSE;
    return FALSE;
 
 
  /* Already cleared by bfd_zalloc above.
  /* Already cleared by bfd_zalloc above.
     bfd_ardata (abfd)->cache = NULL;
     bfd_ardata (abfd)->cache = NULL;
Line 316... Line 317...
        return FALSE;
        return FALSE;
      bfd_ardata (arch_bfd)->cache = hash_table;
      bfd_ardata (arch_bfd)->cache = hash_table;
    }
    }
 
 
  /* Insert new_elt into the hash table by filepos.  */
  /* Insert new_elt into the hash table by filepos.  */
  cache = bfd_zalloc (arch_bfd, sizeof (struct ar_cache));
  cache = (struct ar_cache *) bfd_zalloc (arch_bfd, sizeof (struct ar_cache));
  cache->ptr = filepos;
  cache->ptr = filepos;
  cache->arbfd = new_elt;
  cache->arbfd = new_elt;
  *htab_find_slot (hash_table, (const void *) cache, INSERT) = cache;
  *htab_find_slot (hash_table, (const void *) cache, INSERT) = cache;
 
 
  return TRUE;
  return TRUE;
}
}


 
static bfd *
 
_bfd_find_nested_archive (bfd *arch_bfd, const char *filename)
 
{
 
  bfd *abfd;
 
 
 
  for (abfd = arch_bfd->nested_archives;
 
       abfd != NULL;
 
       abfd = abfd->archive_next)
 
    {
 
      if (strcmp (filename, abfd->filename) == 0)
 
        return abfd;
 
    }
 
  abfd = bfd_openr (filename, NULL);
 
  if (abfd)
 
    {
 
      abfd->archive_next = arch_bfd->nested_archives;
 
      arch_bfd->nested_archives = abfd;
 
    }
 
  return abfd;
 
}
 
 
/* The name begins with space.  Hence the rest of the name is an index into
/* The name begins with space.  Hence the rest of the name is an index into
   the string table.  */
   the string table.  */
 
 
static char *
static char *
get_extended_arelt_filename (bfd *arch, const char *name)
get_extended_arelt_filename (bfd *arch, const char *name, file_ptr *originp)
{
{
  unsigned long index = 0;
  unsigned long index = 0;
 
  const char *endp;
 
 
  /* Should extract string so that I can guarantee not to overflow into
  /* Should extract string so that I can guarantee not to overflow into
     the next region, but I'm too lazy.  */
     the next region, but I'm too lazy.  */
  errno = 0;
  errno = 0;
  /* Skip first char, which is '/' in SVR4 or ' ' in some other variants.  */
  /* Skip first char, which is '/' in SVR4 or ' ' in some other variants.  */
  index = strtol (name + 1, NULL, 10);
  index = strtol (name + 1, (char **) &endp, 10);
  if (errno != 0 || index >= bfd_ardata (arch)->extended_names_size)
  if (errno != 0 || index >= bfd_ardata (arch)->extended_names_size)
    {
    {
      bfd_set_error (bfd_error_malformed_archive);
      bfd_set_error (bfd_error_malformed_archive);
      return NULL;
      return NULL;
    }
    }
 
  /* In a thin archive, a member of an archive-within-an-archive
 
     will have the offset in the inner archive encoded here.  */
 
  if (bfd_is_thin_archive (arch) && endp != NULL && *endp == ':')
 
    {
 
      file_ptr origin = strtol (endp + 1, NULL, 10);
 
 
 
      if (errno != 0)
 
        {
 
          bfd_set_error (bfd_error_malformed_archive);
 
          return NULL;
 
        }
 
      *originp = origin;
 
    }
 
  else
 
    *originp = 0;
 
 
  return bfd_ardata (arch)->extended_names + index;
  return bfd_ardata (arch)->extended_names + index;
}
}
 
 
/* This functions reads an arch header and returns an areltdata pointer, or
/* This functions reads an arch header and returns an areltdata pointer, or
Line 374... Line 412...
  struct areltdata *ared;
  struct areltdata *ared;
  char *filename = NULL;
  char *filename = NULL;
  bfd_size_type namelen = 0;
  bfd_size_type namelen = 0;
  bfd_size_type allocsize = sizeof (struct areltdata) + sizeof (struct ar_hdr);
  bfd_size_type allocsize = sizeof (struct areltdata) + sizeof (struct ar_hdr);
  char *allocptr = 0;
  char *allocptr = 0;
 
  file_ptr origin = 0;
 
 
  if (bfd_bread (hdrp, sizeof (struct ar_hdr), abfd) != sizeof (struct ar_hdr))
  if (bfd_bread (hdrp, sizeof (struct ar_hdr), abfd) != sizeof (struct ar_hdr))
    {
    {
      if (bfd_get_error () != bfd_error_system_call)
      if (bfd_get_error () != bfd_error_system_call)
        bfd_set_error (bfd_error_no_more_archived_files);
        bfd_set_error (bfd_error_no_more_archived_files);
Line 405... Line 444...
  if ((hdr.ar_name[0] == '/'
  if ((hdr.ar_name[0] == '/'
       || (hdr.ar_name[0] == ' '
       || (hdr.ar_name[0] == ' '
           && memchr (hdr.ar_name, '/', ar_maxnamelen (abfd)) == NULL))
           && memchr (hdr.ar_name, '/', ar_maxnamelen (abfd)) == NULL))
      && bfd_ardata (abfd)->extended_names != NULL)
      && bfd_ardata (abfd)->extended_names != NULL)
    {
    {
      filename = get_extended_arelt_filename (abfd, hdr.ar_name);
      filename = get_extended_arelt_filename (abfd, hdr.ar_name, &origin);
      if (filename == NULL)
      if (filename == NULL)
        return NULL;
        return NULL;
    }
    }
  /* BSD4.4-style long filename.
  /* BSD4.4-style long filename.
     Only implemented for reading, so far!  */
     Only implemented for reading, so far!  */
Line 421... Line 460...
      /* BSD-4.4 extended name */
      /* BSD-4.4 extended name */
      namelen = atoi (&hdr.ar_name[3]);
      namelen = atoi (&hdr.ar_name[3]);
      allocsize += namelen + 1;
      allocsize += namelen + 1;
      parsed_size -= namelen;
      parsed_size -= namelen;
 
 
      allocptr = bfd_zalloc (abfd, allocsize);
      allocptr = (char *) bfd_zalloc (abfd, allocsize);
      if (allocptr == NULL)
      if (allocptr == NULL)
        return NULL;
        return NULL;
      filename = (allocptr
      filename = (allocptr
                  + sizeof (struct areltdata)
                  + sizeof (struct areltdata)
                  + sizeof (struct ar_hdr));
                  + sizeof (struct ar_hdr));
Line 442... Line 481...
      /* We judge the end of the name by looking for '/' or ' '.
      /* We judge the end of the name by looking for '/' or ' '.
         Note:  The SYSV format (terminated by '/') allows embedded
         Note:  The SYSV format (terminated by '/') allows embedded
         spaces, so only look for ' ' if we don't find '/'.  */
         spaces, so only look for ' ' if we don't find '/'.  */
 
 
      char *e;
      char *e;
      e = memchr (hdr.ar_name, '\0', ar_maxnamelen (abfd));
      e = (char *) memchr (hdr.ar_name, '\0', ar_maxnamelen (abfd));
      if (e == NULL)
      if (e == NULL)
        {
        {
          e = memchr (hdr.ar_name, '/', ar_maxnamelen (abfd));
          e = (char *) memchr (hdr.ar_name, '/', ar_maxnamelen (abfd));
          if (e == NULL)
          if (e == NULL)
            e = memchr (hdr.ar_name, ' ', ar_maxnamelen (abfd));
            e = (char *) memchr (hdr.ar_name, ' ', ar_maxnamelen (abfd));
        }
        }
 
 
      if (e != NULL)
      if (e != NULL)
        namelen = e - hdr.ar_name;
        namelen = e - hdr.ar_name;
      else
      else
Line 464... Line 503...
      allocsize += namelen + 1;
      allocsize += namelen + 1;
    }
    }
 
 
  if (!allocptr)
  if (!allocptr)
    {
    {
      allocptr = bfd_zalloc (abfd, allocsize);
      allocptr = (char *) bfd_zalloc (abfd, allocsize);
      if (allocptr == NULL)
      if (allocptr == NULL)
        return NULL;
        return NULL;
    }
    }
 
 
  ared = (struct areltdata *) allocptr;
  ared = (struct areltdata *) allocptr;
 
 
  ared->arch_header = allocptr + sizeof (struct areltdata);
  ared->arch_header = allocptr + sizeof (struct areltdata);
  memcpy (ared->arch_header, &hdr, sizeof (struct ar_hdr));
  memcpy (ared->arch_header, &hdr, sizeof (struct ar_hdr));
  ared->parsed_size = parsed_size;
  ared->parsed_size = parsed_size;
 
  ared->origin = origin;
 
 
  if (filename != NULL)
  if (filename != NULL)
    ared->filename = filename;
    ared->filename = filename;
  else
  else
    {
    {
Line 489... Line 529...
    }
    }
 
 
  return ared;
  return ared;
}
}


 
/* Append the relative pathname for a member of the thin archive
 
   to the pathname of the directory containing the archive.  */
 
 
 
static char *
 
append_relative_path (bfd *arch, char *elt_name)
 
{
 
  const char *arch_name = arch->filename;
 
  const char *base_name = lbasename (arch_name);
 
  size_t prefix_len;
 
  char *filename;
 
 
 
  if (base_name == arch_name)
 
    return elt_name;
 
 
 
  prefix_len = base_name - arch_name;
 
  filename = (char *) bfd_alloc (arch, prefix_len + strlen (elt_name) + 1);
 
  if (filename == NULL)
 
    return NULL;
 
 
 
  strncpy (filename, arch_name, prefix_len);
 
  strcpy (filename + prefix_len, elt_name);
 
  return filename;
 
}
 
 
/* This is an internal function; it's mainly used when indexing
/* This is an internal function; it's mainly used when indexing
   through the archive symbol table, but also used to get the next
   through the archive symbol table, but also used to get the next
   element, since it handles the bookkeeping so nicely for us.  */
   element, since it handles the bookkeeping so nicely for us.  */
 
 
bfd *
bfd *
_bfd_get_elt_at_filepos (bfd *archive, file_ptr filepos)
_bfd_get_elt_at_filepos (bfd *archive, file_ptr filepos)
{
{
  struct areltdata *new_areldata;
  struct areltdata *new_areldata;
  bfd *n_nfd;
  bfd *n_nfd;
 
  char *filename;
 
 
  if (archive->my_archive)
  if (archive->my_archive)
    {
    {
      filepos += archive->origin;
      filepos += archive->origin;
      archive = archive->my_archive;
      archive = archive->my_archive;
Line 512... Line 577...
    return n_nfd;
    return n_nfd;
 
 
  if (0 > bfd_seek (archive, filepos, SEEK_SET))
  if (0 > bfd_seek (archive, filepos, SEEK_SET))
    return NULL;
    return NULL;
 
 
  if ((new_areldata = _bfd_read_ar_hdr (archive)) == NULL)
  if ((new_areldata = (struct areltdata *) _bfd_read_ar_hdr (archive)) == NULL)
 
    return NULL;
 
 
 
  filename = new_areldata->filename;
 
 
 
  if (bfd_is_thin_archive (archive))
 
    {
 
      /* This is a proxy entry for an external file.  */
 
      if (! IS_ABSOLUTE_PATH (filename))
 
        {
 
          filename = append_relative_path (archive, filename);
 
          if (filename == NULL)
    return NULL;
    return NULL;
 
        }
 
 
 
      if (new_areldata->origin > 0)
 
        {
 
          /* This proxy entry refers to an element of a nested archive.
 
             Locate the member of that archive and return a bfd for it.  */
 
          bfd *ext_arch = _bfd_find_nested_archive (archive, filename);
 
 
 
          if (ext_arch == NULL
 
              || ! bfd_check_format (ext_arch, bfd_archive))
 
            {
 
              bfd_release (archive, new_areldata);
 
              return NULL;
 
            }
 
          n_nfd = _bfd_get_elt_at_filepos (ext_arch, new_areldata->origin);
 
          if (n_nfd == NULL)
 
            {
 
              bfd_release (archive, new_areldata);
 
              return NULL;
 
            }
 
          n_nfd->proxy_origin = bfd_tell (archive);
 
          return n_nfd;
 
        }
 
      /* It's not an element of a nested archive;
 
         open the external file as a bfd.  */
 
      n_nfd = bfd_openr (filename, NULL);
 
    }
 
  else
 
    {
  n_nfd = _bfd_create_empty_archive_element_shell (archive);
  n_nfd = _bfd_create_empty_archive_element_shell (archive);
 
    }
 
 
  if (n_nfd == NULL)
  if (n_nfd == NULL)
    {
    {
      bfd_release (archive, new_areldata);
      bfd_release (archive, new_areldata);
      return NULL;
      return NULL;
    }
    }
 
 
  n_nfd->origin = bfd_tell (archive);
  n_nfd->proxy_origin = bfd_tell (archive);
 
 
 
  if (bfd_is_thin_archive (archive))
 
    {
 
      n_nfd->origin = 0;
 
    }
 
  else
 
    {
 
      n_nfd->origin = n_nfd->proxy_origin;
 
      n_nfd->filename = filename;
 
    }
 
 
  n_nfd->arelt_data = new_areldata;
  n_nfd->arelt_data = new_areldata;
  n_nfd->filename = new_areldata->filename;
 
 
 
  if (_bfd_add_bfd_to_archive_cache (archive, filepos, n_nfd))
  if (_bfd_add_bfd_to_archive_cache (archive, filepos, n_nfd))
    return n_nfd;
    return n_nfd;
 
 
  /* Huh?  */
  /* Huh?  */
 
  /* FIXME:  n_nfd isn't allocated in the archive's memory pool.
 
     If we reach this point, I think bfd_release will abort.  */
  bfd_release (archive, n_nfd);
  bfd_release (archive, n_nfd);
  bfd_release (archive, new_areldata);
  bfd_release (archive, new_areldata);
  return NULL;
  return NULL;
}
}
 
 
Line 566... Line 684...
*/
*/
 
 
bfd *
bfd *
bfd_openr_next_archived_file (bfd *archive, bfd *last_file)
bfd_openr_next_archived_file (bfd *archive, bfd *last_file)
{
{
  if ((bfd_get_format (archive) != bfd_archive) ||
  if ((bfd_get_format (archive) != bfd_archive)
      (archive->direction == write_direction))
      || (archive->direction == write_direction))
    {
    {
      bfd_set_error (bfd_error_invalid_operation);
      bfd_set_error (bfd_error_invalid_operation);
      return NULL;
      return NULL;
    }
    }
 
 
Line 587... Line 705...
  if (!last_file)
  if (!last_file)
    filestart = bfd_ardata (archive)->first_file_filepos;
    filestart = bfd_ardata (archive)->first_file_filepos;
  else
  else
    {
    {
      unsigned int size = arelt_size (last_file);
      unsigned int size = arelt_size (last_file);
      filestart = last_file->origin + size;
      filestart = last_file->proxy_origin;
 
      if (! bfd_is_thin_archive (archive))
 
        filestart += size;
      if (archive->my_archive)
      if (archive->my_archive)
        filestart -= archive->origin;
        filestart -= archive->origin;
      /* Pad to an even boundary...
      /* Pad to an even boundary...
         Note that last_file->origin can be odd in the case of
         Note that last_file->origin can be odd in the case of
         BSD-4.4-style element with a long odd size.  */
         BSD-4.4-style element with a long odd size.  */
Line 613... Line 733...
      if (bfd_get_error () != bfd_error_system_call)
      if (bfd_get_error () != bfd_error_system_call)
        bfd_set_error (bfd_error_wrong_format);
        bfd_set_error (bfd_error_wrong_format);
      return NULL;
      return NULL;
    }
    }
 
 
  if (strncmp (armag, ARMAG, SARMAG) != 0 &&
  bfd_is_thin_archive (abfd) = (strncmp (armag, ARMAGT, SARMAG) == 0);
      strncmp (armag, ARMAGB, SARMAG) != 0)
 
 
  if (strncmp (armag, ARMAG, SARMAG) != 0
 
      && strncmp (armag, ARMAGB, SARMAG) != 0
 
      && ! bfd_is_thin_archive (abfd))
    return 0;
    return 0;
 
 
  tdata_hold = bfd_ardata (abfd);
  tdata_hold = bfd_ardata (abfd);
 
 
  amt = sizeof (struct artdata);
  amt = sizeof (struct artdata);
  bfd_ardata (abfd) = bfd_zalloc (abfd, amt);
  bfd_ardata (abfd) = (struct artdata *) bfd_zalloc (abfd, amt);
  if (bfd_ardata (abfd) == NULL)
  if (bfd_ardata (abfd) == NULL)
    {
    {
      bfd_ardata (abfd) = tdata_hold;
      bfd_ardata (abfd) = tdata_hold;
      return NULL;
      return NULL;
    }
    }
Line 710... Line 833...
  struct artdata *ardata = bfd_ardata (abfd);
  struct artdata *ardata = bfd_ardata (abfd);
  char *stringbase;
  char *stringbase;
  bfd_size_type parsed_size, amt;
  bfd_size_type parsed_size, amt;
  carsym *set;
  carsym *set;
 
 
  mapdata = _bfd_read_ar_hdr (abfd);
  mapdata = (struct areltdata *) _bfd_read_ar_hdr (abfd);
  if (mapdata == NULL)
  if (mapdata == NULL)
    return FALSE;
    return FALSE;
  parsed_size = mapdata->parsed_size;
  parsed_size = mapdata->parsed_size;
  bfd_release (abfd, mapdata);  /* Don't need it any more.  */
  bfd_release (abfd, mapdata);  /* Don't need it any more.  */
 
 
  raw_armap = bfd_zalloc (abfd, parsed_size);
  raw_armap = (bfd_byte *) bfd_zalloc (abfd, parsed_size);
  if (raw_armap == NULL)
  if (raw_armap == NULL)
    return FALSE;
    return FALSE;
 
 
  if (bfd_bread (raw_armap, parsed_size, abfd) != parsed_size)
  if (bfd_bread (raw_armap, parsed_size, abfd) != parsed_size)
    {
    {
Line 745... Line 868...
  rbase = raw_armap + BSD_SYMDEF_COUNT_SIZE;
  rbase = raw_armap + BSD_SYMDEF_COUNT_SIZE;
  stringbase = ((char *) rbase
  stringbase = ((char *) rbase
                + ardata->symdef_count * BSD_SYMDEF_SIZE
                + ardata->symdef_count * BSD_SYMDEF_SIZE
                + BSD_STRING_COUNT_SIZE);
                + BSD_STRING_COUNT_SIZE);
  amt = ardata->symdef_count * sizeof (carsym);
  amt = ardata->symdef_count * sizeof (carsym);
  ardata->symdefs = bfd_alloc (abfd, amt);
  ardata->symdefs = (struct carsym *) bfd_alloc (abfd, amt);
  if (!ardata->symdefs)
  if (!ardata->symdefs)
    return FALSE;
    return FALSE;
 
 
  for (counter = 0, set = ardata->symdefs;
  for (counter = 0, set = ardata->symdefs;
       counter < ardata->symdef_count;
       counter < ardata->symdef_count;
Line 786... Line 909...
  bfd_vma (*swap) (const void *);
  bfd_vma (*swap) (const void *);
  char int_buf[sizeof (long)];
  char int_buf[sizeof (long)];
  bfd_size_type carsym_size, ptrsize;
  bfd_size_type carsym_size, ptrsize;
  unsigned int i;
  unsigned int i;
 
 
  mapdata = _bfd_read_ar_hdr (abfd);
  mapdata = (struct areltdata *) _bfd_read_ar_hdr (abfd);
  if (mapdata == NULL)
  if (mapdata == NULL)
    return FALSE;
    return FALSE;
  parsed_size = mapdata->parsed_size;
  parsed_size = mapdata->parsed_size;
  bfd_release (abfd, mapdata);  /* Don't need it any more.  */
  bfd_release (abfd, mapdata);  /* Don't need it any more.  */
 
 
Line 831... Line 954...
  ptrsize = (4 * nsymz);
  ptrsize = (4 * nsymz);
 
 
  if (carsym_size + stringsize + 1 <= carsym_size)
  if (carsym_size + stringsize + 1 <= carsym_size)
    return FALSE;
    return FALSE;
 
 
  ardata->symdefs = bfd_zalloc (abfd, carsym_size + stringsize + 1);
  ardata->symdefs = (struct carsym *) bfd_zalloc (abfd,
 
                                                  carsym_size + stringsize + 1);
  if (ardata->symdefs == NULL)
  if (ardata->symdefs == NULL)
    return FALSE;
    return FALSE;
  carsyms = ardata->symdefs;
  carsyms = ardata->symdefs;
  stringbase = ((char *) ardata->symdefs) + carsym_size;
  stringbase = ((char *) ardata->symdefs) + carsym_size;
 
 
  /* Allocate and read in the raw offsets.  */
  /* Allocate and read in the raw offsets.  */
  raw_armap = bfd_alloc (abfd, ptrsize);
  raw_armap = (int *) bfd_alloc (abfd, ptrsize);
  if (raw_armap == NULL)
  if (raw_armap == NULL)
    goto release_symdefs;
    goto release_symdefs;
  if (bfd_bread (raw_armap, ptrsize, abfd) != ptrsize
  if (bfd_bread (raw_armap, ptrsize, abfd) != ptrsize
      || (bfd_bread (stringbase, stringsize, abfd) != stringsize))
      || (bfd_bread (stringbase, stringsize, abfd) != stringsize))
    {
    {
Line 873... Line 997...
  /* Check for a second archive header (as used by PE).  */
  /* Check for a second archive header (as used by PE).  */
  {
  {
    struct areltdata *tmp;
    struct areltdata *tmp;
 
 
    bfd_seek (abfd, ardata->first_file_filepos, SEEK_SET);
    bfd_seek (abfd, ardata->first_file_filepos, SEEK_SET);
    tmp = _bfd_read_ar_hdr (abfd);
    tmp = (struct areltdata *) _bfd_read_ar_hdr (abfd);
    if (tmp != NULL)
    if (tmp != NULL)
      {
      {
        if (tmp->arch_header[0] == '/'
        if (tmp->arch_header[0] == '/'
            && tmp->arch_header[1] == ' ')
            && tmp->arch_header[1] == ' ')
          {
          {
Line 973... Line 1097...
    {
    {
      bfd_has_map (abfd) = FALSE;
      bfd_has_map (abfd) = FALSE;
      return TRUE;
      return TRUE;
    }
    }
 
 
  mapdata = _bfd_read_ar_hdr (abfd);
  mapdata = (struct areltdata *) _bfd_read_ar_hdr (abfd);
  if (mapdata == NULL)
  if (mapdata == NULL)
    return FALSE;
    return FALSE;
 
 
  amt = mapdata->parsed_size;
  amt = mapdata->parsed_size;
  raw_armap = bfd_zalloc (abfd, amt);
  raw_armap = (bfd_byte *) bfd_zalloc (abfd, amt);
  if (raw_armap == NULL)
  if (raw_armap == NULL)
    {
    {
    byebye:
    byebye:
      bfd_release (abfd, mapdata);
      bfd_release (abfd, mapdata);
      return FALSE;
      return FALSE;
Line 1014... Line 1138...
  stringbase = ((char *) raw_armap
  stringbase = ((char *) raw_armap
                + HPUX_SYMDEF_COUNT_SIZE
                + HPUX_SYMDEF_COUNT_SIZE
                + BSD_STRING_COUNT_SIZE);
                + BSD_STRING_COUNT_SIZE);
  rbase = (bfd_byte *) stringbase + stringsize;
  rbase = (bfd_byte *) stringbase + stringsize;
  amt = ardata->symdef_count * BSD_SYMDEF_SIZE;
  amt = ardata->symdef_count * BSD_SYMDEF_SIZE;
  ardata->symdefs = bfd_alloc (abfd, amt);
  ardata->symdefs = (struct carsym *) bfd_alloc (abfd, amt);
  if (!ardata->symdefs)
  if (!ardata->symdefs)
    return FALSE;
    return FALSE;
 
 
  for (counter = 0, set = ardata->symdefs;
  for (counter = 0, set = ardata->symdefs;
       counter < ardata->symdef_count;
       counter < ardata->symdef_count;
Line 1071... Line 1195...
          bfd_ardata (abfd)->extended_names = NULL;
          bfd_ardata (abfd)->extended_names = NULL;
          bfd_ardata (abfd)->extended_names_size = 0;
          bfd_ardata (abfd)->extended_names_size = 0;
          return TRUE;
          return TRUE;
        }
        }
 
 
      namedata = _bfd_read_ar_hdr (abfd);
      namedata = (struct areltdata *) _bfd_read_ar_hdr (abfd);
      if (namedata == NULL)
      if (namedata == NULL)
        return FALSE;
        return FALSE;
 
 
      amt = namedata->parsed_size;
      amt = namedata->parsed_size;
      if (amt + 1 == 0)
      if (amt + 1 == 0)
        goto byebye;
        goto byebye;
 
 
      bfd_ardata (abfd)->extended_names_size = amt;
      bfd_ardata (abfd)->extended_names_size = amt;
      bfd_ardata (abfd)->extended_names = bfd_zalloc (abfd, amt + 1);
      bfd_ardata (abfd)->extended_names = (char *) bfd_zalloc (abfd, amt + 1);
      if (bfd_ardata (abfd)->extended_names == NULL)
      if (bfd_ardata (abfd)->extended_names == NULL)
        {
        {
        byebye:
        byebye:
          bfd_release (abfd, namedata);
          bfd_release (abfd, namedata);
          return FALSE;
          return FALSE;
Line 1108... Line 1232...
        char *ext_names = bfd_ardata (abfd)->extended_names;
        char *ext_names = bfd_ardata (abfd)->extended_names;
        char *temp = ext_names;
        char *temp = ext_names;
        char *limit = temp + namedata->parsed_size;
        char *limit = temp + namedata->parsed_size;
        for (; temp < limit; ++temp)
        for (; temp < limit; ++temp)
          {
          {
            if (*temp == '\012')
            if (*temp == ARFMAG[1])
              temp[temp > ext_names && temp[-1] == '/' ? -1 : 0] = '\0';
              temp[temp > ext_names && temp[-1] == '/' ? -1 : 0] = '\0';
            if (*temp == '\\')
            if (*temp == '\\')
              *temp = '/';
              *temp = '/';
          }
          }
        *limit = '\0';
        *limit = '\0';
Line 1188... Line 1312...
    filename = file;
    filename = file;
  return filename;
  return filename;
}
}
#endif
#endif
 
 
 
/* Adjust a relative path name based on the reference path.  */
 
 
 
static const char *
 
adjust_relative_path (const char * path, const char * ref_path)
 
{
 
  static char *pathbuf = NULL;
 
  static int pathbuf_len = 0;
 
  const char *pathp = path;
 
  const char *refp = ref_path;
 
  int element_count = 0;
 
  int len;
 
  char *newp;
 
 
 
  /* Remove common leading path elements.  */
 
  for (;;)
 
    {
 
      const char *e1 = pathp;
 
      const char *e2 = refp;
 
 
 
      while (*e1 && ! IS_DIR_SEPARATOR (*e1))
 
        ++e1;
 
      while (*e2 && ! IS_DIR_SEPARATOR (*e2))
 
        ++e2;
 
      if (*e1 == '\0' || *e2 == '\0' || e1 - pathp != e2 - refp
 
          || strncmp (pathp, refp, e1 - pathp) != 0)
 
        break;
 
      pathp = e1 + 1;
 
      refp = e2 + 1;
 
    }
 
 
 
  /* For each leading path element in the reference path,
 
     insert "../" into the path.  */
 
  for (; *refp; ++refp)
 
    if (IS_DIR_SEPARATOR (*refp))
 
      ++element_count;
 
  len = 3 * element_count + strlen (path) + 1;
 
 
 
  if (len > pathbuf_len)
 
    {
 
      if (pathbuf != NULL)
 
        free (pathbuf);
 
      pathbuf_len = 0;
 
      pathbuf = (char *) bfd_malloc (len);
 
      if (pathbuf == NULL)
 
        return path;
 
      pathbuf_len = len;
 
    }
 
 
 
  newp = pathbuf;
 
  while (element_count-- > 0)
 
    {
 
      /* FIXME: Support Windows style path separators as well.  */
 
      strcpy (newp, "../");
 
      newp += 3;
 
    }
 
  strcpy (newp, pathp);
 
 
 
  return pathbuf;
 
}
 
 
/* Build a BFD style extended name table.  */
/* Build a BFD style extended name table.  */
 
 
bfd_boolean
bfd_boolean
_bfd_archive_bsd_construct_extended_name_table (bfd *abfd,
_bfd_archive_bsd_construct_extended_name_table (bfd *abfd,
                                                char **tabloc,
                                                char **tabloc,
Line 1230... Line 1414...
{
{
  unsigned int maxname = abfd->xvec->ar_max_namelen;
  unsigned int maxname = abfd->xvec->ar_max_namelen;
  bfd_size_type total_namelen = 0;
  bfd_size_type total_namelen = 0;
  bfd *current;
  bfd *current;
  char *strptr;
  char *strptr;
 
  const char *last_filename;
 
  long last_stroff;
 
 
  *tablen = 0;
  *tablen = 0;
 
  last_filename = NULL;
 
 
  /* Figure out how long the table should be.  */
  /* Figure out how long the table should be.  */
  for (current = abfd->archive_head;
  for (current = abfd->archive_head;
       current != NULL;
       current != NULL;
       current = current->archive_next)
       current = current->archive_next)
    {
    {
      const char *normal;
      const char *normal;
      unsigned int thislen;
      unsigned int thislen;
 
 
 
      if (bfd_is_thin_archive (abfd))
 
        {
 
          const char *filename = current->filename;
 
 
 
          /* If the element being added is a member of another archive
 
             (i.e., we are flattening), use the containing archive's name.  */
 
          if (current->my_archive
 
              && ! bfd_is_thin_archive (current->my_archive))
 
            filename = current->my_archive->filename;
 
 
 
          /* If the path is the same as the previous path seen,
 
             reuse it.  This can happen when flattening a thin
 
             archive that contains other archives.  */
 
          if (last_filename && strcmp (last_filename, filename) == 0)
 
            continue;
 
 
 
          last_filename = filename;
 
 
 
          /* If the path is relative, adjust it relative to
 
             the containing archive. */
 
          if (! IS_ABSOLUTE_PATH (filename)
 
              && ! IS_ABSOLUTE_PATH (abfd->filename))
 
            normal = adjust_relative_path (filename, abfd->filename);
 
          else
 
            normal = filename;
 
 
 
          /* In a thin archive, always store the full pathname
 
             in the extended name table.  */
 
          total_namelen += strlen (normal) + 1;
 
          if (trailing_slash)
 
            /* Leave room for trailing slash.  */
 
            ++total_namelen;
 
 
 
          continue;
 
        }
 
 
      normal = normalize (current, current->filename);
      normal = normalize (current, current->filename);
      if (normal == NULL)
      if (normal == NULL)
        return FALSE;
        return FALSE;
 
 
      thislen = strlen (normal);
      thislen = strlen (normal);
Line 1281... Line 1504...
    }
    }
 
 
  if (total_namelen == 0)
  if (total_namelen == 0)
    return TRUE;
    return TRUE;
 
 
  *tabloc = bfd_zalloc (abfd, total_namelen);
  *tabloc = (char *) bfd_zalloc (abfd, total_namelen);
  if (*tabloc == NULL)
  if (*tabloc == NULL)
    return FALSE;
    return FALSE;
 
 
  *tablen = total_namelen;
  *tablen = total_namelen;
  strptr = *tabloc;
  strptr = *tabloc;
 
 
 
  last_filename = NULL;
 
  last_stroff = 0;
 
 
  for (current = abfd->archive_head;
  for (current = abfd->archive_head;
       current != NULL;
       current != NULL;
       current = current->archive_next)
       current = current->archive_next)
    {
    {
      const char *normal;
      const char *normal;
      unsigned int thislen;
      unsigned int thislen;
 
      long stroff;
 
      const char *filename = current->filename;
 
 
      normal = normalize (current, current->filename);
      if (bfd_is_thin_archive (abfd))
 
        {
 
          /* If the element being added is a member of another archive
 
             (i.e., we are flattening), use the containing archive's name.  */
 
          if (current->my_archive
 
              && ! bfd_is_thin_archive (current->my_archive))
 
            filename = current->my_archive->filename;
 
          /* If the path is the same as the previous path seen,
 
             reuse it.  This can happen when flattening a thin
 
             archive that contains other archives.
 
             If the path is relative, adjust it relative to
 
             the containing archive.  */
 
          if (last_filename && strcmp (last_filename, filename) == 0)
 
            normal = last_filename;
 
          else if (! IS_ABSOLUTE_PATH (filename)
 
                   && ! IS_ABSOLUTE_PATH (abfd->filename))
 
            normal = adjust_relative_path (filename, abfd->filename);
 
          else
 
            normal = filename;
 
        }
 
      else
 
        {
 
          normal = normalize (current, filename);
      if (normal == NULL)
      if (normal == NULL)
        return FALSE;
        return FALSE;
 
        }
 
 
      thislen = strlen (normal);
      thislen = strlen (normal);
      if (thislen > maxname)
      if (thislen > maxname || bfd_is_thin_archive (abfd))
        {
        {
          /* Works for now; may need to be re-engineered if we
          /* Works for now; may need to be re-engineered if we
             encounter an oddball archive format and want to
             encounter an oddball archive format and want to
             generalise this hack.  */
             generalise this hack.  */
          struct ar_hdr *hdr = arch_hdr (current);
          struct ar_hdr *hdr = arch_hdr (current);
 
          if (normal == last_filename)
 
            stroff = last_stroff;
 
          else
 
            {
          strcpy (strptr, normal);
          strcpy (strptr, normal);
          if (! trailing_slash)
          if (! trailing_slash)
            strptr[thislen] = '\012';
                strptr[thislen] = ARFMAG[1];
          else
          else
            {
            {
              strptr[thislen] = '/';
              strptr[thislen] = '/';
              strptr[thislen + 1] = '\012';
                  strptr[thislen + 1] = ARFMAG[1];
 
                }
 
              stroff = strptr - *tabloc;
 
              last_stroff = stroff;
            }
            }
          hdr->ar_name[0] = ar_padchar (current);
          hdr->ar_name[0] = ar_padchar (current);
          _bfd_ar_spacepad (hdr->ar_name + 1, maxname - 1, "%-ld",
          if (bfd_is_thin_archive (abfd) && current->origin > 0)
                            strptr - *tabloc);
            {
 
              int len = snprintf (hdr->ar_name + 1, maxname - 1, "%-ld:",
 
                                  stroff);
 
              _bfd_ar_spacepad (hdr->ar_name + 1 + len, maxname - 1 - len,
 
                                "%-ld",
 
                                current->origin - sizeof (struct ar_hdr));
 
            }
 
          else
 
            _bfd_ar_spacepad (hdr->ar_name + 1, maxname - 1, "%-ld", stroff);
 
          if (normal != last_filename)
 
            {
          strptr += thislen + 1;
          strptr += thislen + 1;
          if (trailing_slash)
          if (trailing_slash)
            ++strptr;
            ++strptr;
 
              last_filename = filename;
 
            }
        }
        }
    }
    }
 
 
  return TRUE;
  return TRUE;
}
}
Line 1368... Line 1638...
  bfd_size_type amt;
  bfd_size_type amt;
 
 
  if (member && (member->flags & BFD_IN_MEMORY) != 0)
  if (member && (member->flags & BFD_IN_MEMORY) != 0)
    {
    {
      /* Assume we just "made" the member, and fake it.  */
      /* Assume we just "made" the member, and fake it.  */
      struct bfd_in_memory *bim = member->iostream;
      struct bfd_in_memory *bim = (struct bfd_in_memory *) member->iostream;
      time (&status.st_mtime);
      time (&status.st_mtime);
      status.st_uid = getuid ();
      status.st_uid = getuid ();
      status.st_gid = getgid ();
      status.st_gid = getgid ();
      status.st_mode = 0644;
      status.st_mode = 0644;
      status.st_size = bim->size;
      status.st_size = bim->size;
Line 1381... Line 1651...
    {
    {
      bfd_set_error (bfd_error_system_call);
      bfd_set_error (bfd_error_system_call);
      return NULL;
      return NULL;
    }
    }
 
 
 
  /* If the caller requested that the BFD generate deterministic output,
 
     fake values for modification time, UID, GID, and file mode.  */
 
  if ((abfd->flags & BFD_DETERMINISTIC_OUTPUT) != 0)
 
    {
 
      status.st_mtime = 0;
 
      status.st_uid = 0;
 
      status.st_gid = 0;
 
      status.st_mode = 0644;
 
    }
 
 
  amt = sizeof (struct ar_hdr) + sizeof (struct areltdata);
  amt = sizeof (struct ar_hdr) + sizeof (struct areltdata);
  ared = bfd_zalloc (abfd, amt);
  ared = (struct areltdata *) bfd_zalloc (abfd, amt);
  if (ared == NULL)
  if (ared == NULL)
    return NULL;
    return NULL;
  hdr = (struct ar_hdr *) (((char *) ared) + sizeof (struct areltdata));
  hdr = (struct ar_hdr *) (((char *) ared) + sizeof (struct areltdata));
 
 
  /* ar headers are space padded, not null padded!  */
  /* ar headers are space padded, not null padded!  */
Line 1591... Line 1871...
 
 
#ifdef HAVE_DOS_BASED_FILE_SYSTEM
#ifdef HAVE_DOS_BASED_FILE_SYSTEM
  {
  {
    /* We could have foo/bar\\baz, or foo\\bar, or d:bar.  */
    /* We could have foo/bar\\baz, or foo\\bar, or d:bar.  */
    char *bslash = strrchr (pathname, '\\');
    char *bslash = strrchr (pathname, '\\');
 
 
    if (filename == NULL || (bslash != NULL && bslash > filename))
    if (filename == NULL || (bslash != NULL && bslash > filename))
      filename = bslash;
      filename = bslash;
    if (filename == NULL && pathname[0] != '\0' && pathname[1] == ':')
    if (filename == NULL && pathname[0] != '\0' && pathname[1] == ':')
      filename = pathname + 1;
      filename = pathname + 1;
  }
  }
Line 1608... Line 1889...
  length = strlen (filename);
  length = strlen (filename);
 
 
  if (length <= maxlen)
  if (length <= maxlen)
    memcpy (hdr->ar_name, filename, length);
    memcpy (hdr->ar_name, filename, length);
  else
  else
    {                           /* pathname: meet procrustes */
    {
 
      /* pathname: meet procrustes.  */
      memcpy (hdr->ar_name, filename, maxlen);
      memcpy (hdr->ar_name, filename, maxlen);
      if ((filename[length - 2] == '.') && (filename[length - 1] == 'o'))
      if ((filename[length - 2] == '.') && (filename[length - 1] == 'o'))
        {
        {
          hdr->ar_name[maxlen - 2] = '.';
          hdr->ar_name[maxlen - 2] = '.';
          hdr->ar_name[maxlen - 1] = 'o';
          hdr->ar_name[maxlen - 1] = 'o';
Line 1636... Line 1918...
  bfd_boolean makemap = bfd_has_map (arch);
  bfd_boolean makemap = bfd_has_map (arch);
  /* If no .o's, don't bother to make a map.  */
  /* If no .o's, don't bother to make a map.  */
  bfd_boolean hasobjects = FALSE;
  bfd_boolean hasobjects = FALSE;
  bfd_size_type wrote;
  bfd_size_type wrote;
  int tries;
  int tries;
 
  char *armag;
 
 
  /* Verify the viability of all entries; if any of them live in the
  /* Verify the viability of all entries; if any of them live in the
     filesystem (as opposed to living in an archive open for input)
     filesystem (as opposed to living in an archive open for input)
     then construct a fresh ar_hdr for them.  */
     then construct a fresh ar_hdr for them.  */
  for (current = arch->archive_head;
  for (current = arch->archive_head;
Line 1679... Line 1962...
                 (arch, &etable, &elength, &ename)))
                 (arch, &etable, &elength, &ename)))
    return FALSE;
    return FALSE;
 
 
  if (bfd_seek (arch, (file_ptr) 0, SEEK_SET) != 0)
  if (bfd_seek (arch, (file_ptr) 0, SEEK_SET) != 0)
    return FALSE;
    return FALSE;
  wrote = bfd_bwrite (ARMAG, SARMAG, arch);
  armag = ARMAG;
 
  if (bfd_is_thin_archive (arch))
 
    armag = ARMAGT;
 
  wrote = bfd_bwrite (armag, SARMAG, arch);
  if (wrote != SARMAG)
  if (wrote != SARMAG)
    return FALSE;
    return FALSE;
 
 
  if (makemap && hasobjects)
  if (makemap && hasobjects)
    {
    {
Line 1705... Line 1991...
           != sizeof (struct ar_hdr))
           != sizeof (struct ar_hdr))
          || bfd_bwrite (etable, elength, arch) != elength)
          || bfd_bwrite (etable, elength, arch) != elength)
        return FALSE;
        return FALSE;
      if ((elength % 2) == 1)
      if ((elength % 2) == 1)
        {
        {
          if (bfd_bwrite ("\012", 1, arch) != 1)
          if (bfd_bwrite (&ARFMAG[1], 1, arch) != 1)
            return FALSE;
            return FALSE;
        }
        }
    }
    }
 
 
  for (current = arch->archive_head;
  for (current = arch->archive_head;
Line 1722... Line 2008...
 
 
      /* Write ar header.  */
      /* Write ar header.  */
      if (bfd_bwrite (hdr, sizeof (*hdr), arch)
      if (bfd_bwrite (hdr, sizeof (*hdr), arch)
          != sizeof (*hdr))
          != sizeof (*hdr))
        return FALSE;
        return FALSE;
 
      if (bfd_is_thin_archive (arch))
 
        continue;
      if (bfd_seek (current, (file_ptr) 0, SEEK_SET) != 0)
      if (bfd_seek (current, (file_ptr) 0, SEEK_SET) != 0)
        goto input_err;
        goto input_err;
 
 
      while (remaining)
      while (remaining)
        {
        {
          unsigned int amt = DEFAULT_BUFFERSIZE;
          unsigned int amt = DEFAULT_BUFFERSIZE;
 
 
          if (amt > remaining)
          if (amt > remaining)
            amt = remaining;
            amt = remaining;
          errno = 0;
          errno = 0;
          if (bfd_bread (buffer, amt, current) != amt)
          if (bfd_bread (buffer, amt, current) != amt)
            {
            {
Line 1740... Line 2030...
            }
            }
          if (bfd_bwrite (buffer, amt, arch) != amt)
          if (bfd_bwrite (buffer, amt, arch) != amt)
            return FALSE;
            return FALSE;
          remaining -= amt;
          remaining -= amt;
        }
        }
 
 
      if ((arelt_size (current) % 2) == 1)
      if ((arelt_size (current) % 2) == 1)
        {
        {
          if (bfd_bwrite ("\012", 1, arch) != 1)
          if (bfd_bwrite (&ARFMAG[1], 1, arch) != 1)
            return FALSE;
            return FALSE;
        }
        }
    }
    }
 
 
  if (makemap && hasobjects)
  if (makemap && hasobjects)
Line 1796... Line 2087...
  if (elength != 0)
  if (elength != 0)
    elength += sizeof (struct ar_hdr);
    elength += sizeof (struct ar_hdr);
  elength += elength % 2;
  elength += elength % 2;
 
 
  amt = orl_max * sizeof (struct orl);
  amt = orl_max * sizeof (struct orl);
  map = bfd_malloc (amt);
  map = (struct orl *) bfd_malloc (amt);
  if (map == NULL)
  if (map == NULL)
    goto error_return;
    goto error_return;
 
 
  /* We put the symbol names on the arch objalloc, and then discard
  /* We put the symbol names on the arch objalloc, and then discard
     them when done.  */
     them when done.  */
  first_name = bfd_alloc (arch, 1);
  first_name = (char *) bfd_alloc (arch, 1);
  if (first_name == NULL)
  if (first_name == NULL)
    goto error_return;
    goto error_return;
 
 
  /* Drop all the files called __.SYMDEF, we're going to make our own.  */
  /* Drop all the files called __.SYMDEF, we're going to make our own.  */
  while (arch->archive_head &&
  while (arch->archive_head
         strcmp (arch->archive_head->filename, "__.SYMDEF") == 0)
         && strcmp (arch->archive_head->filename, "__.SYMDEF") == 0)
    arch->archive_head = arch->archive_head->archive_next;
    arch->archive_head = arch->archive_head->archive_next;
 
 
  /* Map over each element.  */
  /* Map over each element.  */
  for (current = arch->archive_head;
  for (current = arch->archive_head;
       current != NULL;
       current != NULL;
Line 1834... Line 2125...
              if (storage > syms_max)
              if (storage > syms_max)
                {
                {
                  if (syms_max > 0)
                  if (syms_max > 0)
                    free (syms);
                    free (syms);
                  syms_max = storage;
                  syms_max = storage;
                  syms = bfd_malloc (syms_max);
                  syms = (asymbol **) bfd_malloc (syms_max);
                  if (syms == NULL)
                  if (syms == NULL)
                    goto error_return;
                    goto error_return;
                }
                }
              symcount = bfd_canonicalize_symtab (current, syms);
              symcount = bfd_canonicalize_symtab (current, syms);
              if (symcount < 0)
              if (symcount < 0)
Line 1849... Line 2140...
              for (src_count = 0; src_count < symcount; src_count++)
              for (src_count = 0; src_count < symcount; src_count++)
                {
                {
                  flagword flags = (syms[src_count])->flags;
                  flagword flags = (syms[src_count])->flags;
                  asection *sec = syms[src_count]->section;
                  asection *sec = syms[src_count]->section;
 
 
                  if ((flags & BSF_GLOBAL ||
                  if ((flags & BSF_GLOBAL
                       flags & BSF_WEAK ||
                       || flags & BSF_WEAK
                       flags & BSF_INDIRECT ||
                       || flags & BSF_INDIRECT
                       bfd_is_com_section (sec))
                       || bfd_is_com_section (sec))
                      && ! bfd_is_und_section (sec))
                      && ! bfd_is_und_section (sec))
                    {
                    {
                      bfd_size_type namelen;
                      bfd_size_type namelen;
                      struct orl *new_map;
                      struct orl *new_map;
 
 
                      /* This symbol will go into the archive header.  */
                      /* This symbol will go into the archive header.  */
                      if (orl_count == orl_max)
                      if (orl_count == orl_max)
                        {
                        {
                          orl_max *= 2;
                          orl_max *= 2;
                          amt = orl_max * sizeof (struct orl);
                          amt = orl_max * sizeof (struct orl);
                          new_map = bfd_realloc (map, amt);
                          new_map = (struct orl *) bfd_realloc (map, amt);
                          if (new_map == NULL)
                          if (new_map == NULL)
                            goto error_return;
                            goto error_return;
 
 
                          map = new_map;
                          map = new_map;
                        }
                        }
 
 
                      namelen = strlen (syms[src_count]->name);
                      namelen = strlen (syms[src_count]->name);
                      amt = sizeof (char *);
                      amt = sizeof (char *);
                      map[orl_count].name = bfd_alloc (arch, amt);
                      map[orl_count].name = (char **) bfd_alloc (arch, amt);
                      if (map[orl_count].name == NULL)
                      if (map[orl_count].name == NULL)
                        goto error_return;
                        goto error_return;
                      *(map[orl_count].name) = bfd_alloc (arch, namelen + 1);
                      *(map[orl_count].name) = (char *) bfd_alloc (arch,
 
                                                                   namelen + 1);
                      if (*(map[orl_count].name) == NULL)
                      if (*(map[orl_count].name) == NULL)
                        goto error_return;
                        goto error_return;
                      strcpy (*(map[orl_count].name), syms[src_count]->name);
                      strcpy (*(map[orl_count].name), syms[src_count]->name);
                      map[orl_count].u.abfd = current;
                      map[orl_count].u.abfd = current;
                      map[orl_count].namidx = stridx;
                      map[orl_count].namidx = stridx;
Line 1938... Line 2230...
  bfd *last_elt = current;      /* Last element arch seen.  */
  bfd *last_elt = current;      /* Last element arch seen.  */
  bfd_byte temp[4];
  bfd_byte temp[4];
  unsigned int count;
  unsigned int count;
  struct ar_hdr hdr;
  struct ar_hdr hdr;
  struct stat statbuf;
  struct stat statbuf;
 
  long uid, gid;
 
 
  firstreal = mapsize + elength + sizeof (struct ar_hdr) + SARMAG;
  firstreal = mapsize + elength + sizeof (struct ar_hdr) + SARMAG;
 
 
  stat (arch->filename, &statbuf);
  stat (arch->filename, &statbuf);
 
  if ((arch->flags & BFD_DETERMINISTIC_OUTPUT) == 0)
 
    {
 
      /* Remember the timestamp, to keep it holy.  But fudge it a little.  */
 
      bfd_ardata (arch)->armap_timestamp = (statbuf.st_mtime
 
                                            + ARMAP_TIME_OFFSET);
 
      uid = getuid();
 
      gid = getgid();
 
    }
 
  else
 
    {
 
      /* If deterministic, we use 0 as the timestamp in the map.
 
         Some linkers may require that the archive filesystem modification
 
         time is less than (or near to) the archive map timestamp.  Those
 
         linkers should not be used with deterministic mode.  (GNU ld and
 
         Gold do not have this restriction.)  */
 
      bfd_ardata (arch)->armap_timestamp = 0;
 
      uid = 0;
 
      gid = 0;
 
    }
 
 
  memset (&hdr, ' ', sizeof (struct ar_hdr));
  memset (&hdr, ' ', sizeof (struct ar_hdr));
  memcpy (hdr.ar_name, RANLIBMAG, strlen (RANLIBMAG));
  memcpy (hdr.ar_name, RANLIBMAG, strlen (RANLIBMAG));
  /* Remember the timestamp, to keep it holy.  But fudge it a little.  */
 
  bfd_ardata (arch)->armap_timestamp = statbuf.st_mtime + ARMAP_TIME_OFFSET;
 
  bfd_ardata (arch)->armap_datepos = (SARMAG
  bfd_ardata (arch)->armap_datepos = (SARMAG
                                      + offsetof (struct ar_hdr, ar_date[0]));
                                      + offsetof (struct ar_hdr, ar_date[0]));
  _bfd_ar_spacepad (hdr.ar_date, sizeof (hdr.ar_date), "%ld",
  _bfd_ar_spacepad (hdr.ar_date, sizeof (hdr.ar_date), "%ld",
                    bfd_ardata (arch)->armap_timestamp);
                    bfd_ardata (arch)->armap_timestamp);
  _bfd_ar_spacepad (hdr.ar_uid, sizeof (hdr.ar_uid), "%ld", getuid ());
  _bfd_ar_spacepad (hdr.ar_uid, sizeof (hdr.ar_uid), "%ld", uid);
  _bfd_ar_spacepad (hdr.ar_gid, sizeof (hdr.ar_gid), "%ld", getgid ());
  _bfd_ar_spacepad (hdr.ar_gid, sizeof (hdr.ar_gid), "%ld", gid);
  _bfd_ar_spacepad (hdr.ar_size, sizeof (hdr.ar_size), "%-10ld", mapsize);
  _bfd_ar_spacepad (hdr.ar_size, sizeof (hdr.ar_size), "%-10ld", mapsize);
  memcpy (hdr.ar_fmag, ARFMAG, 2);
  memcpy (hdr.ar_fmag, ARFMAG, 2);
  if (bfd_bwrite (&hdr, sizeof (struct ar_hdr), arch)
  if (bfd_bwrite (&hdr, sizeof (struct ar_hdr), arch)
      != sizeof (struct ar_hdr))
      != sizeof (struct ar_hdr))
    return FALSE;
    return FALSE;
Line 2019... Line 2330...
_bfd_archive_bsd_update_armap_timestamp (bfd *arch)
_bfd_archive_bsd_update_armap_timestamp (bfd *arch)
{
{
  struct stat archstat;
  struct stat archstat;
  struct ar_hdr hdr;
  struct ar_hdr hdr;
 
 
 
  /* If creating deterministic archives, just leave the timestamp as-is.  */
 
  if ((arch->flags & BFD_DETERMINISTIC_OUTPUT) != 0)
 
    return TRUE;
 
 
  /* Flush writes, get last-write timestamp from file, and compare it
  /* Flush writes, get last-write timestamp from file, and compare it
     to the timestamp IN the file.  */
     to the timestamp IN the file.  */
  bfd_flush (arch);
  bfd_flush (arch);
  if (bfd_stat (arch, &archstat) == -1)
  if (bfd_stat (arch, &archstat) == -1)
    {
    {
      bfd_perror (_("Reading archive file mod timestamp"));
      bfd_perror (_("Reading archive file mod timestamp"));
 
 
      /* Can't read mod time for some reason.  */
      /* Can't read mod time for some reason.  */
      return TRUE;
      return TRUE;
    }
    }
  if (archstat.st_mtime <= bfd_ardata (arch)->armap_timestamp)
  if (((long) archstat.st_mtime) <= bfd_ardata (arch)->armap_timestamp)
    /* OK by the linker's rules.  */
    /* OK by the linker's rules.  */
    return TRUE;
    return TRUE;
 
 
  /* Update the timestamp.  */
  /* Update the timestamp.  */
  bfd_ardata (arch)->armap_timestamp = archstat.st_mtime + ARMAP_TIME_OFFSET;
  bfd_ardata (arch)->armap_timestamp = archstat.st_mtime + ARMAP_TIME_OFFSET;
Line 2103... Line 2418...
  memset (&hdr, ' ', sizeof (struct ar_hdr));
  memset (&hdr, ' ', sizeof (struct ar_hdr));
  hdr.ar_name[0] = '/';
  hdr.ar_name[0] = '/';
  _bfd_ar_spacepad (hdr.ar_size, sizeof (hdr.ar_size), "%-10ld",
  _bfd_ar_spacepad (hdr.ar_size, sizeof (hdr.ar_size), "%-10ld",
                    mapsize);
                    mapsize);
  _bfd_ar_spacepad (hdr.ar_date, sizeof (hdr.ar_date), "%ld",
  _bfd_ar_spacepad (hdr.ar_date, sizeof (hdr.ar_date), "%ld",
                    time (NULL));
                    ((arch->flags & BFD_DETERMINISTIC_OUTPUT) == 0
 
                     ? time (NULL) : 0));
  /* This, at least, is what Intel coff sets the values to.  */
  /* This, at least, is what Intel coff sets the values to.  */
  _bfd_ar_spacepad (hdr.ar_uid, sizeof (hdr.ar_uid), "%ld", 0);
  _bfd_ar_spacepad (hdr.ar_uid, sizeof (hdr.ar_uid), "%ld", 0);
  _bfd_ar_spacepad (hdr.ar_gid, sizeof (hdr.ar_gid), "%ld", 0);
  _bfd_ar_spacepad (hdr.ar_gid, sizeof (hdr.ar_gid), "%ld", 0);
  _bfd_ar_spacepad (hdr.ar_mode, sizeof (hdr.ar_mode), "%-7lo", 0);
  _bfd_ar_spacepad (hdr.ar_mode, sizeof (hdr.ar_mode), "%-7lo", 0);
  memcpy (hdr.ar_fmag, ARFMAG, 2);
  memcpy (hdr.ar_fmag, ARFMAG, 2);
Line 2137... Line 2453...
        {
        {
          if (!bfd_write_bigendian_4byte_int (arch, archive_member_file_ptr))
          if (!bfd_write_bigendian_4byte_int (arch, archive_member_file_ptr))
            return FALSE;
            return FALSE;
          count++;
          count++;
        }
        }
 
      archive_member_file_ptr += sizeof (struct ar_hdr);
 
      if (! bfd_is_thin_archive (arch))
 
        {
      /* Add size of this archive entry.  */
      /* Add size of this archive entry.  */
      archive_member_file_ptr += arelt_size (current) + sizeof (struct ar_hdr);
          archive_member_file_ptr += arelt_size (current);
      /* Remember aboout the even alignment.  */
          /* Remember about the even alignment.  */
      archive_member_file_ptr += archive_member_file_ptr % 2;
      archive_member_file_ptr += archive_member_file_ptr % 2;
 
        }
      current = current->archive_next;
      current = current->archive_next;
    }
    }
 
 
  /* Now write the strings themselves.  */
  /* Now write the strings themselves.  */
  for (count = 0; count < symbol_count; count++)
  for (count = 0; count < symbol_count; count++)

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.