This is the mail archive of the
binutils-cvs@sourceware.org
mailing list for the binutils project.
[binutils-gdb] Fix internal error in fix_errata on aarch64.
- From: Cary Coutant <ccoutant at sourceware dot org>
- To: bfd-cvs at sourceware dot org
- Date: 30 Nov 2017 23:08:40 -0000
- Subject: [binutils-gdb] Fix internal error in fix_errata on aarch64.
https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=fd6798fa2d6f0374d45449c4212869da93623b1e
commit fd6798fa2d6f0374d45449c4212869da93623b1e
Author: Peter Smith <peter.smith@linaro.org>
Date: Thu Nov 30 15:07:26 2017 -0800
Fix internal error in fix_errata on aarch64.
The addresses of erratum stubs can be changed by relaxation passes, and
need to be updated.
gold/
PR gold/20765
* aarch64.cc (Aarch64_relobj::update_erratum_address): New method.
(AArch64_relobj::scan_errata): Update addresses in stub table after
relaxation pass.
Diff:
---
gold/ChangeLog | 7 +++++++
gold/aarch64.cc | 25 +++++++++++++++++++++++++
2 files changed, 32 insertions(+)
diff --git a/gold/ChangeLog b/gold/ChangeLog
index 1245da5..43a3d70 100644
--- a/gold/ChangeLog
+++ b/gold/ChangeLog
@@ -1,4 +1,11 @@
2017-11-30 Peter Smith <peter.smith@linaro.org>
+
+ PR gold/20765
+ * aarch64.cc (Aarch64_relobj::update_erratum_address): New method.
+ (AArch64_relobj::scan_errata): Update addresses in stub table after
+ relaxation pass.
+
+2017-11-30 Peter Smith <peter.smith@linaro.org>
Cary Coutant <ccoutant@gmail.com>
PR gold/20765
diff --git a/gold/aarch64.cc b/gold/aarch64.cc
index 04da01d..5e702db 100644
--- a/gold/aarch64.cc
+++ b/gold/aarch64.cc
@@ -1031,6 +1031,18 @@ public:
set_erratum_address(AArch64_address addr)
{ this->erratum_address_ = addr; }
+ // Later relaxation passes of may alter the recorded erratum and destination
+ // address. Given an up to date output section address of shidx_ in
+ // relobj_ we can derive the erratum_address and destination address.
+ void
+ update_erratum_address(AArch64_address output_section_addr)
+ {
+ const int BPI = AArch64_insn_utilities<big_endian>::BYTES_PER_INSN;
+ AArch64_address updated_addr = output_section_addr + this->sh_offset_;
+ this->set_erratum_address(updated_addr);
+ this->set_destination_address(updated_addr + BPI);
+ }
+
// Comparator used to group Erratum_stubs in a set by (obj, shndx,
// sh_offset). We do not include 'type' in the calculation, because there is
// at most one stub type at (obj, shndx, sh_offset).
@@ -2304,6 +2316,19 @@ AArch64_relobj<size, big_endian>::scan_errata(
output_address = poris->address();
}
+ // Update the addresses in previously generated erratum stubs. Unlike when
+ // we scan relocations for stubs, if section addresses have changed due to
+ // other relaxations we are unlikely to scan the same erratum instances
+ // again.
+ The_stub_table* stub_table = this->stub_table(shndx);
+ if (stub_table)
+ {
+ std::pair<Erratum_stub_set_iter, Erratum_stub_set_iter>
+ ipair(stub_table->find_erratum_stubs_for_input_section(this, shndx));
+ for (Erratum_stub_set_iter p = ipair.first; p != ipair.second; ++p)
+ (*p)->update_erratum_address(output_address);
+ }
+
section_size_type input_view_size = 0;
const unsigned char* input_view =
this->section_contents(shndx, &input_view_size, false);