aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bfd/ChangeLog5
-rw-r--r--bfd/elf32-arm.c32
-rw-r--r--ld/testsuite/ChangeLog7
-rw-r--r--ld/testsuite/ld-arm/arm-elf.exp3
-rw-r--r--ld/testsuite/ld-arm/farcall-group-limit.d21
-rw-r--r--ld/testsuite/ld-arm/farcall-group3.s9
-rw-r--r--ld/testsuite/ld-arm/farcall-group4.s13
7 files changed, 82 insertions, 8 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index bc12f9f..f15e157 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,5 +1,10 @@
2009-03-05 Christophe Lyon <christophe.lyon@st.com>
+ * elf32-arm.c (group_sections): Take next section size into
+ account before accepting to group it.
+
+2009-03-05 Christophe Lyon <christophe.lyon@st.com>
+
* elf32-arm.c (arm_type_of_stub): Handle long branches targetting
PLT entries.
(elf32_arm_final_link_relocate): Likewise.
diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
index 607ba04..f534290 100644
--- a/bfd/elf32-arm.c
+++ b/bfd/elf32-arm.c
@@ -3554,11 +3554,20 @@ group_sections (struct elf32_arm_link_hash_table *htab,
bfd_size_type total;
curr = head;
- total = head->size;
- while ((next = NEXT_SEC (curr)) != NULL
- && ((total += next->output_offset - curr->output_offset)
- < stub_group_size))
+ total = 0;
+ while ((next = NEXT_SEC (curr)) != NULL)
+ {
+ if ( (total + next->output_offset - curr->output_offset
+ + next->size)
+ < stub_group_size )
+ {
+ total += next->output_offset - curr->output_offset;
+ }
+ else
+ break;
+
curr = next;
+ }
/* OK, the size from the start to the start of CURR is less
than stub_group_size and thus can be handled by one stub
@@ -3579,11 +3588,18 @@ group_sections (struct elf32_arm_link_hash_table *htab,
bytes after the stub section can be handled by it too. */
if (!stubs_always_after_branch)
{
- total = 0;
- while (next != NULL
- && ((total += next->output_offset - head->output_offset)
- < stub_group_size))
+ total = head->size;
+ while (next != NULL)
{
+ if ( (total + next->output_offset - head->output_offset
+ + next->size)
+ < stub_group_size )
+ {
+ total += next->output_offset - head->output_offset;
+ }
+ else
+ break;
+
head = next;
next = NEXT_SEC (head);
htab->stub_group[head->id].link_sec = curr;
diff --git a/ld/testsuite/ChangeLog b/ld/testsuite/ChangeLog
index 693a93b..9c9f1e7 100644
--- a/ld/testsuite/ChangeLog
+++ b/ld/testsuite/ChangeLog
@@ -1,5 +1,12 @@
2009-03-05 Christophe Lyon <christophe.lyon@st.com>
+ * ld-arm/arm-elf.exp: Add new farcall-group-limit test.
+ * ld-arm/farcall-group-limit.d: New file.
+ * ld-arm/farcall-group3.s: New file.
+ * ld-arm/farcall-group4.s: New file.
+
+2009-03-05 Christophe Lyon <christophe.lyon@st.com>
+
* ld-arm/arm-elf.exp: Add 2 more tests to check long branch stubs
in PLT context.
* ld-arm/farcall-mixed-app-v5.d: New file.
diff --git a/ld/testsuite/ld-arm/arm-elf.exp b/ld/testsuite/ld-arm/arm-elf.exp
index 0dfc441..b9c7513 100644
--- a/ld/testsuite/ld-arm/arm-elf.exp
+++ b/ld/testsuite/ld-arm/arm-elf.exp
@@ -338,6 +338,9 @@ set armeabitests {
{"Group size=2" "-Ttext 0x1000 --section-start .foo=0x2003020 --stub-group-size=2" "" {farcall-group.s farcall-group2.s}
{{objdump -d farcall-group-size2.d}}
"farcall-group-size2"}
+ {"Group size limit" "-Ttext 0x1000 --section-start .far=0x2003020" "" {farcall-group3.s farcall-group4.s}
+ {{objdump -d farcall-group-limit.d}}
+ "farcall-group-limit"}
{"Mixed ARM/Thumb dynamic application with farcalls" "tmpdir/mixed-lib.so -T arm-dyn.ld --section-start .far_arm=0x2100000 --section-start .far_thumb=0x2200000" ""
{farcall-mixed-app.s}
diff --git a/ld/testsuite/ld-arm/farcall-group-limit.d b/ld/testsuite/ld-arm/farcall-group-limit.d
new file mode 100644
index 0000000..204dcd8
--- /dev/null
+++ b/ld/testsuite/ld-arm/farcall-group-limit.d
@@ -0,0 +1,21 @@
+
+.*: file format .*
+
+Disassembly of section .text:
+
+00001000 <_start>:
+ 1000: eb000000 bl 1008 <__bar_veneer>
+ 1004: 00000000 andeq r0, r0, r0
+
+00001008 <__bar_veneer>:
+ 1008: e51ff004 ldr pc, \[pc, #-4\] ; 100c <__bar_veneer\+0x4>
+ 100c: 02003020 .word 0x02003020
+
+00001010 <myfunc>:
+ ...
+ 2001010: eb000802 bl 2003020 <bar>
+
+Disassembly of section .far:
+
+02003020 <bar>:
+ 2003020: e12fff1e bx lr
diff --git a/ld/testsuite/ld-arm/farcall-group3.s b/ld/testsuite/ld-arm/farcall-group3.s
new file mode 100644
index 0000000..ea2ce7f
--- /dev/null
+++ b/ld/testsuite/ld-arm/farcall-group3.s
@@ -0,0 +1,9 @@
+@ Test to ensure that ARM calls exceeding 32Mb generate stubs,
+@ and that stubs are correctly inserted between input sections
+@ when one contribution size exceeds the limit.
+
+ .text
+ .global bar
+ .global _start
+_start:
+ bl bar
diff --git a/ld/testsuite/ld-arm/farcall-group4.s b/ld/testsuite/ld-arm/farcall-group4.s
new file mode 100644
index 0000000..17f503b
--- /dev/null
+++ b/ld/testsuite/ld-arm/farcall-group4.s
@@ -0,0 +1,13 @@
+@ Test to ensure that ARM calls exceeding 32Mb generate stubs,
+@ and that a large input section forces stub insertion before its
+@ contribution.
+
+ .text
+myfunc:
+ .space 0x2000000
+ bl bar
+
+ .section .far, "xa"
+ .global bar
+bar:
+ bx lr