Fix ppc64 ELFv1 assertion failure
authorAlan Modra <amodra@gmail.com>
Wed, 22 Jul 2015 09:41:22 +0000 (19:11 +0930)
committerAlan Modra <amodra@gmail.com>
Wed, 22 Jul 2015 09:50:38 +0000 (19:20 +0930)
Bogus assembly can hit an assertion in opd_entry_value when the symbol
referenced by a function descriptor is undefined.  Worse, the code
after the assert copies unitialised memory to return the code section.
This uninitialised pointer can later be dereferencd, possibly causing
a linker segmentation fault.

* elf64-ppc.c (opd_entry_value): Remove assertion.  Instead,
return -1 if symbol referenced is not defined.  Tidy.

bfd/ChangeLog
bfd/elf64-ppc.c

index 36a5b60..c7915b5 100644 (file)
@@ -1,3 +1,8 @@
+2015-07-22  Alan Modra  <amodra@gmail.com>
+
+       * elf64-ppc.c (opd_entry_value): Remove assertion.  Instead,
+       return -1 if symbol referenced is not defined.  Tidy.
+
 2015-07-20  Alan Modra  <amodra@gmail.com>
 
        * po/SRC-POTFILES.in: Regenerate.
index 468e8bf..ef08164 100644 (file)
@@ -6034,14 +6034,13 @@ opd_entry_value (asection *opd_sec,
                  if (rh != NULL)
                    {
                      rh = elf_follow_link (rh);
-                     BFD_ASSERT (rh->root.type == bfd_link_hash_defined
-                                 || rh->root.type == bfd_link_hash_defweak);
-                     val = rh->root.u.def.value;
-                     sec = rh->root.u.def.section;
-                     if (sec->owner != opd_bfd)
+                     if (rh->root.type != bfd_link_hash_defined
+                         && rh->root.type != bfd_link_hash_defweak)
+                       break;
+                     if (rh->root.u.def.section->owner == opd_bfd)
                        {
-                         sec = NULL;
-                         val = (bfd_vma) -1;
+                         val = rh->root.u.def.value;
+                         sec = rh->root.u.def.section;
                        }
                    }
                }