aboutsummaryrefslogtreecommitdiff
path: root/ld
diff options
context:
space:
mode:
authorAlan Modra <amodra@gmail.com>2018-01-18 22:06:40 +1030
committerAlan Modra <amodra@gmail.com>2018-01-18 22:25:21 +1030
commit691d2e9af211ff8dd5fa8c96cb961b73a78394d7 (patch)
treee50abd115ac31293734bb1f32b9fd2a07adcf926 /ld
parent7ab820379890dc68699ba5acf8ab4f03053fa2b0 (diff)
downloadbinutils-691d2e9af211ff8dd5fa8c96cb961b73a78394d7.zip
binutils-691d2e9af211ff8dd5fa8c96cb961b73a78394d7.tar.gz
binutils-691d2e9af211ff8dd5fa8c96cb961b73a78394d7.tar.bz2
PowerPC PLT stub alignment fixes
Asking for ppc32 plt call stubs to be aligned at 32 byte boundaries didn't quite work. For ld.bfd they were spaced 32 bytes apart, but only started on a 16 byte boundary. ld.gold also didn't get it right. Finding that bug made me check over the ppc64 plt stub alignment, where I found that negative values for alignment (meaning align to minimize boundary crossing) were not accepted. Since no one has complained about that, I guess I could have removed the feature from ld.bfd documentation, but I've opted instead to correct the code. I've also added an optional alignment paramenter for ppc32 --plt-align, for some consistency with gold and ppc64 ld.bfd. bfd/ * elf32-ppc.c (ppc_elf_create_glink): Correct alignment of .glink. * elf64-ppc.c (ppc64_elf_size_stubs): Handle negative plt_stub_align. (ppc64_elf_build_stubs): Likewise. gold/ * powerpc.cc (param_plt_align): New function supplying default --plt-align values. Use it.. (Stub_table::plt_call_align): ..here, and.. (Output_data_glink::global_entry_align): ..here. (Stub_table::stub_align): Correct 32-bit minimum alignment. ld/ * emultempl/ppc32elf.em: Support optional --plt-align arg. * emultempl/ppc64elf.em: Support negative --plt-align arg.
Diffstat (limited to 'ld')
-rw-r--r--ld/ChangeLog5
-rw-r--r--ld/emultempl/ppc32elf.em13
-rw-r--r--ld/emultempl/ppc64elf.em4
3 files changed, 18 insertions, 4 deletions
diff --git a/ld/ChangeLog b/ld/ChangeLog
index 9ee555b..3801705 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,3 +1,8 @@
+2018-01-18 Alan Modra <amodra@gmail.com>
+
+ * emultempl/ppc32elf.em: Support optional --plt-align arg.
+ * emultempl/ppc64elf.em: Support negative --plt-align arg.
+
2018-01-17 Alan Modra <amodra@gmail.com>
* emultempl/ppc32elf.em (params): Init new field.
diff --git a/ld/emultempl/ppc32elf.em b/ld/emultempl/ppc32elf.em
index 4e71a78..3007fb2 100644
--- a/ld/emultempl/ppc32elf.em
+++ b/ld/emultempl/ppc32elf.em
@@ -271,7 +271,7 @@ if test -z "$VXWORKS_BASE_EM_FILE" ; then
{ "bss-plt", no_argument, NULL, OPTION_OLD_PLT },
{ "speculate-indirect-jumps", no_argument, NULL, OPTION_SPECULATE_INDIRECT_JUMPS },
{ "no-speculate-indirect-jumps", no_argument, NULL, OPTION_NO_SPECULATE_INDIRECT_JUMPS },
- { "plt-align", no_argument, NULL, OPTION_PLT_ALIGN },
+ { "plt-align", optional_argument, NULL, OPTION_PLT_ALIGN },
{ "no-plt-align", no_argument, NULL, OPTION_NO_PLT_ALIGN },
{ "sdata-got", no_argument, NULL, OPTION_OLD_GOT },'
fi
@@ -369,7 +369,16 @@ PARSE_AND_LIST_ARGS_CASES=${PARSE_AND_LIST_ARGS_CASES}'
break;
case OPTION_PLT_ALIGN:
- params.plt_stub_align = 5;
+ if (optarg != NULL)
+ {
+ char *end;
+ unsigned long val = strtoul (optarg, &end, 0);
+ if (*end || val > 5)
+ einfo (_("%P%F: invalid --plt-align `%s'\''\n"), optarg);
+ params.plt_stub_align = val;
+ }
+ else
+ params.plt_stub_align = 5;
break;
case OPTION_NO_PLT_ALIGN:
diff --git a/ld/emultempl/ppc64elf.em b/ld/emultempl/ppc64elf.em
index c7c27b0..0baa424 100644
--- a/ld/emultempl/ppc64elf.em
+++ b/ld/emultempl/ppc64elf.em
@@ -872,8 +872,8 @@ PARSE_AND_LIST_ARGS_CASES=${PARSE_AND_LIST_ARGS_CASES}'
if (optarg != NULL)
{
char *end;
- unsigned long val = strtoul (optarg, &end, 0);
- if (*end || val > 8)
+ long val = strtol (optarg, &end, 0);
+ if (*end || (unsigned long) val + 8 > 16)
einfo (_("%P%F: invalid --plt-align `%s'\''\n"), optarg);
params.plt_stub_align = val;
}