aboutsummaryrefslogtreecommitdiffstats
path: root/main/binutils/fix-powerpc64-out-ot-line-save-restore.patch
diff options
context:
space:
mode:
authorNatanael Copa <ncopa@alpinelinux.org>2018-05-18 09:04:37 +0000
committerNatanael Copa <ncopa@alpinelinux.org>2018-05-30 22:30:12 +0200
commitcb56f87d3a50fb6ef7d3b95bf6167f95fab881a2 (patch)
treee5ed578fed85924d79bf8ec95c435ce24155d49f /main/binutils/fix-powerpc64-out-ot-line-save-restore.patch
parent1bbd727b16f144e132af8f3c4a41f6b754aff086 (diff)
downloadaports-cb56f87d3a50fb6ef7d3b95bf6167f95fab881a2.tar.bz2
aports-cb56f87d3a50fb6ef7d3b95bf6167f95fab881a2.tar.xz
main/binutils: backport fix for ppc64le
This fixes clang testsuite. Patch was taken from upstream binutils-2_30-branch https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;a=shortlog;h=refs/heads/binutils-2_30-branch Upstream report: https://sourceware.org/ml/binutils/2018-03/msg00183.html
Diffstat (limited to 'main/binutils/fix-powerpc64-out-ot-line-save-restore.patch')
-rw-r--r--main/binutils/fix-powerpc64-out-ot-line-save-restore.patch93
1 files changed, 93 insertions, 0 deletions
diff --git a/main/binutils/fix-powerpc64-out-ot-line-save-restore.patch b/main/binutils/fix-powerpc64-out-ot-line-save-restore.patch
new file mode 100644
index 0000000000..56ec7ede40
--- /dev/null
+++ b/main/binutils/fix-powerpc64-out-ot-line-save-restore.patch
@@ -0,0 +1,93 @@
+From d66deb71f1537e2e30dccdfda22eed5d46ec47eb Mon Sep 17 00:00:00 2001
+From: Alan Modra <amodra@gmail.com>
+Date: Wed, 14 Mar 2018 22:09:33 +1030
+Subject: [PATCH] PowerPC64 debian bug 886264, out-of-line save/restore
+ functions
+
+This calculation in relocate_section
+
+ if (stub_entry->stub_type == ppc_stub_save_res)
+ relocation += (stub_sec->output_offset
+ + stub_sec->output_section->vma
+ + stub_sec->size - htab->sfpr->size
+ - htab->sfpr->output_offset
+ - htab->sfpr->output_section->vma);
+
+to adjust from the original out-of-line save/restore function address
+in sfpr to a copy at the end of stub_sec goes wrong when stub_sec is
+padded, because the copy is no longer at the end of stub_sec. The
+solution is to pad before copying sfpr, so the copy is always at the
+end of stub_sec.
+
+ * elf64-ppc.c (sfpr_define): Adjust for stub_sec size having
+ sfpr size added before defining alias symbols.
+ (ppc64_elf_build_stubs): Add stub section padding before
+ copying sfpr contents and defining save/restore alias symbols.
+
+(cherry picked from commit 7dda8d3cf3b089bb7e03c4cdbec827fc6a188c88)
+---
+ bfd/ChangeLog | 9 +++++++++
+ bfd/elf64-ppc.c | 33 ++++++++++++++++++---------------
+ 2 files changed, 27 insertions(+), 15 deletions(-)
+
+diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c
+index 6fcdff0..039294f 100644
+--- a/bfd/elf64-ppc.c
++++ b/bfd/elf64-ppc.c
+@@ -6645,7 +6645,7 @@ sfpr_define (struct bfd_link_info *info,
+ {
+ s->root.type = bfd_link_hash_defined;
+ s->root.u.def.section = stub_sec;
+- s->root.u.def.value = (stub_sec->size
++ s->root.u.def.value = (stub_sec->size - htab->sfpr->size
+ + h->elf.root.u.def.value);
+ s->ref_regular = 1;
+ s->def_regular = 1;
+@@ -13232,20 +13232,7 @@ ppc64_elf_build_stubs (struct bfd_link_info *info,
+
+ for (group = htab->group; group != NULL; group = group->next)
+ if (group->needs_save_res)
+- {
+- stub_sec = group->stub_sec;
+- memcpy (stub_sec->contents + stub_sec->size, htab->sfpr->contents,
+- htab->sfpr->size);
+- if (htab->params->emit_stub_syms)
+- {
+- unsigned int i;
+-
+- for (i = 0; i < ARRAY_SIZE (save_res_funcs); i++)
+- if (!sfpr_define (info, &save_res_funcs[i], stub_sec))
+- return FALSE;
+- }
+- stub_sec->size += htab->sfpr->size;
+- }
++ group->stub_sec->size += htab->sfpr->size;
+
+ if (htab->relbrlt != NULL)
+ htab->relbrlt->reloc_count = 0;
+@@ -13259,6 +13246,22 @@ ppc64_elf_build_stubs (struct bfd_link_info *info,
+ }
+
+ for (group = htab->group; group != NULL; group = group->next)
++ if (group->needs_save_res)
++ {
++ stub_sec = group->stub_sec;
++ memcpy (stub_sec->contents + stub_sec->size - htab->sfpr->size,
++ htab->sfpr->contents, htab->sfpr->size);
++ if (htab->params->emit_stub_syms)
++ {
++ unsigned int i;
++
++ for (i = 0; i < ARRAY_SIZE (save_res_funcs); i++)
++ if (!sfpr_define (info, &save_res_funcs[i], stub_sec))
++ return FALSE;
++ }
++ }
++
++ for (group = htab->group; group != NULL; group = group->next)
+ if ((stub_sec = group->stub_sec) != NULL)
+ {
+ stub_sec_count += 1;
+--
+2.9.3
+