diff options
author | Nick Clifton <nickc@redhat.com> | 2016-02-09 09:56:21 +0000 |
---|---|---|
committer | Nick Clifton <nickc@redhat.com> | 2016-02-09 09:56:21 +0000 |
commit | 2ea53e003163338a403d5afbb2046cafb8f3abe9 (patch) | |
tree | 4239dc30b45ff76536a55578194b080124302ec1 /bfd/elfnn-aarch64.c | |
parent | 24f5f69a8a1d09c317a5f28d324fca73a8a0b930 (diff) | |
download | gdb-2ea53e003163338a403d5afbb2046cafb8f3abe9.zip gdb-2ea53e003163338a403d5afbb2046cafb8f3abe9.tar.gz gdb-2ea53e003163338a403d5afbb2046cafb8f3abe9.tar.bz2 |
Add a more helpful warning message to explain why some AArch64 relocations can overflow.
bfd * elfnn-aarch64.c (elfNN_aarch64_relocate_section): Add a more
helpful warning message to explain why certain AArch64 relocs
might overflow.
ld * testsuite/ld-aarch64/reloc-overflow-bad.d: New test.
* testsuite/ld-aarch64/reloc-overflow-1.s: New source file.
* testsuite/ld-aarch64/reloc-overflow-2.s: New source file.
* testsuite/ld-aarch64/aarch64-elf.exp: Run the new test.
Diffstat (limited to 'bfd/elfnn-aarch64.c')
-rw-r--r-- | bfd/elfnn-aarch64.c | 35 |
1 files changed, 31 insertions, 4 deletions
diff --git a/bfd/elfnn-aarch64.c b/bfd/elfnn-aarch64.c index 292470df..99acab4 100644 --- a/bfd/elfnn-aarch64.c +++ b/bfd/elfnn-aarch64.c @@ -6405,10 +6405,6 @@ elfNN_aarch64_relocate_section (bfd *output_bfd, break; } - if (!save_addend) - addend = 0; - - /* Dynamic relocs are not propagated for SEC_DEBUGGING sections because such sections are not SEC_ALLOC and thus ld.so will not process them. */ @@ -6448,6 +6444,34 @@ elfNN_aarch64_relocate_section (bfd *output_bfd, name, input_bfd, input_section, rel->r_offset); return FALSE; } + /* Overflow can occur when a variable is referenced with a type + that has a larger alignment than the type with which it was + declared. eg: + file1.c: extern int foo; int a (void) { return foo; } + file2.c: char bar, foo, baz; + If the variable is placed into a data section at an offset + that is incompatible with the larger alignment requirement + overflow will occur. (Strictly speaking this is not overflow + but rather an alignment problem, but the bfd_reloc_ error + enum does not have a value to cover that situation). + + Try to catch this situation here and provide a more helpful + error message to the user. */ + if (addend & ((1 << howto->rightshift) - 1) + /* FIXME: Are we testing all of the appropriate reloc + types here ? */ + && (real_r_type == BFD_RELOC_AARCH64_LD_LO19_PCREL + || real_r_type == BFD_RELOC_AARCH64_LDST16_LO12 + || real_r_type == BFD_RELOC_AARCH64_LDST32_LO12 + || real_r_type == BFD_RELOC_AARCH64_LDST64_LO12 + || real_r_type == BFD_RELOC_AARCH64_LDST128_LO12)) + { + info->callbacks->warning + (info, _("One possible cause of this error is that the \ +symbol is being referenced in the indicated code as if it had a larger \ +alignment than was declared where it was defined."), + name, input_bfd, input_section, rel->r_offset); + } break; case bfd_reloc_undefined: @@ -6482,6 +6506,9 @@ elfNN_aarch64_relocate_section (bfd *output_bfd, break; } } + + if (!save_addend) + addend = 0; } return TRUE; |