https://sourceware.org/bugzilla/show_bug.cgi?id=6511

John David Anglin <danglin at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|RESOLVED                    |REOPENED
         Resolution|FIXED                       |---
                 CC|                            |danglin at gcc dot gnu.org
             Target|hppa64-hp-hpux11.00         |hppa64-hp-hpux11.00,
                   |                            |hppa64-linux-gnu

--- Comment #14 from John David Anglin <danglin at gcc dot gnu.org> ---
The fix applied in comment 13 is insufficient.  When hh->owner is NULL,
hh->sym_indx also hasn't been initialized and it's zero.  This leads
to a bogus UND symbol in the .dynsym section.

This is current code:

          /* If we are creating a shared library, then we will have to
             create a runtime relocation for the symbol to properly
             initialize the .opd entry.  Make sure the symbol gets
             added to the dynamic symbol table.  */
          if (bfd_link_pic (x->info)
              && (hh == NULL || (hh->eh.dynindx == -1)))
            {
              bfd *owner;
              /* PR 6511: Default to using the dynamic symbol table.  */
              owner = (hh->owner ? hh->owner: eh->root.u.def.section->owner);

              if (!bfd_elf_link_record_local_dynamic_symbol
                    (x->info, owner, hh->sym_indx))
                return false;
            }

Currently, hh->owner and hh->sym_indx are initialized here in
elf64_hppa_check_relocs:

      if (hh)
        {
          /* Stash away enough information to be able to find this symbol
             regardless of whether or not it is local or global.  */
          hh->owner = abfd;
          hh->sym_indx = r_symndx;
        }

Although the comment indicates this needs to occur for both local and
global symbols, hh->owner and hh->sym_indx are only initialized for global
symbols when hh is not NULL:

      if (r_symndx >= symtab_hdr->sh_info)
        {
          /* We're dealing with a global symbol -- find its hash entry
             and mark it as being referenced.  */
          long indx = r_symndx - symtab_hdr->sh_info;
          hh = hppa_elf_hash_entry (elf_sym_hashes (abfd)[indx]);
          while (hh->eh.root.type == bfd_link_hash_indirect
                 || hh->eh.root.type == bfd_link_hash_warning)
            hh = hppa_elf_hash_entry (hh->eh.root.u.i.link);

          /* PR15323, ref flags aren't set for references in the same
             object.  */
          if (!hh->eh.root.linker_def && !hh->eh.root.ldscript_def)
            hh->eh.ref_regular = 1;
          else
            hh = NULL;
        }
      else
        hh = NULL;

The simplest fix seems to be to somehow find the symbol index in
allocate_global_data_opd when hh->owner is not initialized.  But I'm
not seeing an easy way to do this when we have a local symbol.

Problem occurs trying to link ld.so.new in glibc.  The bcmp symbol in
string/memcmp.c is not handled correctly.

libc_hidden_builtin_def(memcmp)
#ifdef weak_alias
# undef bcmp
weak_alias (memcmp, bcmp)
#endif

#undef __memcmpeq
strong_alias (memcmp, __memcmpeq)
libc_hidden_def(__memcmpeq)

-- 
You are receiving this mail because:
You are on the CC list for the bug.

Reply via email to