This is the mail archive of the binutils@sources.redhat.com mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

[Fwd: Patch, aix import symbols in archives]



Ooops all that work and I forgot to attach the file... 
Here it is.

Tom



-- 
Tom Rix 
GCC Engineer
trix@redhat.com
256.704.9201


This patch improves the linker's handling of shared objects, specifically import
symbols contained in archives.  The loader section of each member of the archive
is searched for needed import symbols.  

As a side effect,  this also fixes a problem with the existing dynamic obj in
lib check.  Aix lib's can mix 32 and 64 bit objects in the same library and
bfd_openr_next_archived_file can return a valid, for the archive, object with an
invalid magic # for the current link. 

-- 
Tom Rix 
GCC Engineer
trix@redhat.com
256.704.9201



2001-08-13 Tom Rix <trix@redhat.com>

	* xcofflink.c: (xcoff_link_check_dynamic_ar_import_symbols) New 
	function. 
	(_bfd_xcoff_bfd_ink_add_symbols): Check for exported import symbols. 
	Fix checking over correct bitness of archive element. 
	(xcoff_link_input_bfd): Allow abs relocations for imported symbols.

Index: xcofflink.c
===================================================================
RCS file: /cvs/cvsfiles/devo/bfd/xcofflink.c,v
retrieving revision 1.75.86.4
diff -c -p -r1.75.86.4 xcofflink.c
*** xcofflink.c	2001/01/30 21:37:40	1.75.86.4
--- xcofflink.c	2001/08/13 17:46:34
*************** static boolean xcoff_link_check_ar_symbo
*** 128,133 ****
--- 128,135 ----
    PARAMS ((bfd *, struct bfd_link_info *, boolean *));
  static boolean xcoff_link_check_dynamic_ar_symbols
    PARAMS ((bfd *, struct bfd_link_info *, boolean *));
+ static boolean xcoff_link_check_dynamic_ar_import_symbols
+   PARAMS ((bfd *, struct bfd_link_info *, boolean *));
  static bfd_size_type xcoff_find_reloc
    PARAMS ((struct internal_reloc *, bfd_size_type, bfd_vma));
  static boolean xcoff_link_add_symbols PARAMS ((bfd *, struct bfd_link_info *));
*************** _bfd_xcoff_bfd_link_add_symbols (abfd, i
*** 590,596 ****
           they will not appear in the archive map even though they
           should, perhaps, be included.  If the archive has no map, we
           just consider each object file in turn, since that apparently
!          is what the AIX native linker does.  */
        if (bfd_has_map (abfd))
  	{
  	  if (! (_bfd_generic_link_add_archive_symbols
--- 592,600 ----
           they will not appear in the archive map even though they
           should, perhaps, be included.  If the archive has no map, we
           just consider each object file in turn, since that apparently
!          is what the AIX native linker does.  
! 
! 	 Imported symbols only exit is loader section of the element. */
        if (bfd_has_map (abfd))
  	{
  	  if (! (_bfd_generic_link_add_archive_symbols
*************** _bfd_xcoff_bfd_link_add_symbols (abfd, i
*** 602,625 ****
  	bfd *member;
  
  	member = bfd_openr_next_archived_file (abfd, (bfd *) NULL);
! 	while (member != NULL)
! 	  {
! 	    if (bfd_check_format (member, bfd_object)
! 		&& (! bfd_has_map (abfd)
! 		    || ((member->flags & DYNAMIC) != 0
! 			&& (member->flags & HAS_SYMS) == 0)))
! 	      {
! 		boolean needed;
! 
! 		if (! xcoff_link_check_archive_element (member, info, &needed))
  		  return false;
- 		if (needed)
- 		  member->archive_pass = -1;
  	      }
! 	    member = bfd_openr_next_archived_file (abfd, member);
  	  }
        }
- 
        return true;
  
      default:
--- 606,645 ----
  	bfd *member;
  
  	member = bfd_openr_next_archived_file (abfd, (bfd *) NULL);
! 	while (member != NULL) {
! 	  /* 64 mixed with 32 bit elements
! 	     Since Aix big archives can mix the order of the elements,
! 	     need to check that the bitness of the element is ok before
! 	     proceding */
! 	  if (bfd_check_format (member, bfd_object) &&
! 	      info->hash->creator == member->xvec) {
! 	    boolean needed;
! 	    
! 	    if (! bfd_has_map (abfd) || 
! 		((member->flags & DYNAMIC) != 0 && 
! 		 (member->flags & HAS_SYMS) == 0)) {
! 		
! 	      if (! xcoff_link_check_archive_element (member, info, &needed))
! 		return false;
! 	    } else if (bfd_has_map (abfd) &&
! 		       (member->flags & DYNAMIC) != 0) {
! 		
! 	      if (! xcoff_link_check_dynamic_ar_import_symbols (member, info, 
! 								&needed))
! 		return false;
! 		  
! 	      if (true == needed) {
! 		if (! xcoff_link_add_symbols (member, info))
  		  return false;
  	      }
! 	    }
! 	    
! 	    if (needed)
! 	      member->archive_pass = -1;
  	  }
+ 	  member = bfd_openr_next_archived_file (abfd, member);
+ 	}
        }
        return true;
  
      default:
*************** xcoff_link_check_ar_symbols (abfd, info,
*** 749,754 ****
--- 769,861 ----
  }
  
  /* Look through the loader symbols to see if this dynamic object
+    should be included in the link. */
+ 
+ static boolean
+ xcoff_link_check_dynamic_ar_import_symbols (abfd, info, pneeded)
+      bfd *abfd;
+      struct bfd_link_info *info;
+      boolean *pneeded;
+ {
+   asection *lsec;
+   bfd_byte *contents;
+   struct internal_ldhdr ldhdr;
+   const char *strings;
+   bfd_byte *elsym, *elsymend;
+ 
+   *pneeded = false;
+ 
+   lsec = bfd_get_section_by_name (abfd, ".loader");
+   if (lsec == NULL)
+     {
+       /* There are no symbols, so don't try to include it.  */
+       return true;
+     }
+ 
+   if (! xcoff_get_section_contents (abfd, lsec))
+     return false;
+   contents = coff_section_data (abfd, lsec)->contents;
+ 
+   bfd_xcoff_swap_ldhdr_in (abfd, contents, &ldhdr);
+ 
+   strings = (char *) contents + ldhdr.l_stoff;
+ 
+   elsym = contents + bfd_xcoff_loader_symbol_offset(abfd, &ldhdr);
+ 
+   elsymend = elsym + ldhdr.l_nsyms * bfd_xcoff_ldsymsz(abfd);
+   for (; elsym < elsymend; elsym += bfd_xcoff_ldsymsz(abfd))
+     {
+       struct internal_ldsym ldsym;
+       char nambuf[SYMNMLEN + 1];
+       const char *name;
+       struct bfd_link_hash_entry *h;
+ 
+       bfd_xcoff_swap_ldsym_in (abfd, elsym, &ldsym);
+ 
+       /* We are only interested in exported imported symbols.  */
+       if (((ldsym.l_smtype & L_EXPORT) == 0) ||
+ 	  ((ldsym.l_smtype & L_IMPORT) == 0))
+ 	continue;
+ 
+       if (ldsym._l._l_l._l_zeroes == 0)
+ 	name = strings + ldsym._l._l_l._l_offset;
+       else
+ 	{
+ 	  memcpy (nambuf, ldsym._l._l_name, SYMNMLEN);
+ 	  nambuf[SYMNMLEN] = '\0';
+ 	  name = nambuf;
+ 	}
+ 
+       h = bfd_link_hash_lookup (info->hash, name, false, false, true);
+ 
+       /* We are only interested in symbols that are currently
+          undefined.  At this point we know that we are using an XCOFF
+          hash table.  */
+       if (h != NULL
+ 	  && h->type == bfd_link_hash_undefined
+ 	  && (((struct xcoff_link_hash_entry *) h)->flags
+ 	      & XCOFF_DEF_DYNAMIC) == 0)
+ 	{
+ 	  if (! (*info->callbacks->add_archive_element) (info, abfd, name))
+ 	    return false;
+ 	  *pneeded = true;
+ 	  return true;
+ 	}
+     }
+ 
+   /* We do not need this shared object.  */
+ 
+   if (contents != NULL && ! coff_section_data (abfd, lsec)->keep_contents)
+     {
+       free (coff_section_data (abfd, lsec)->contents);
+       coff_section_data (abfd, lsec)->contents = NULL;
+     }
+ 
+   return true;
+ }
+ 
+ 
+ /* Look through the loader symbols to see if this dynamic object
     should be included in the link.  The native linker uses the loader
     symbols, not the normal symbol table, so we do too.  */
  
*************** xcoff_link_input_bfd (finfo, input_bfd)
*** 5218,5224 ****
  		  ldrel.l_symndx = 1;
  		else if (strcmp (sec->name, ".bss") == 0)
  		  ldrel.l_symndx = 2;
! 		else
  		  {
  		    (*_bfd_error_handler)
  		      (_("%s: loader reloc in unrecognized section `%s'"),
--- 5325,5335 ----
  		  ldrel.l_symndx = 1;
  		else if (strcmp (sec->name, ".bss") == 0)
  		  ldrel.l_symndx = 2;
! 		else if ((sec == bfd_abs_section_ptr) &&
! 			 (h->flags & XCOFF_IMPORT)) {
! 		  /* abs section relocations for import symbols are ok */
! 		  ldrel.l_symndx = 0;
! 		} else
  		  {
  		    (*_bfd_error_handler)
  		      (_("%s: loader reloc in unrecognized section `%s'"),

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]