This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Committed][AArch64] Implement branch over stub section.


Ensure that injection of a stub section does not break a link where
there is an xpectation that flow of control can pass from one input
section to another simply by linking the input sections in series.

The solution here is to allow stub sections to be inserted after any
input section (existing behaviour), but inject an additional branch at
the start of each stub section such that control flow falling into the
stub section will branch over the stub section.

2015-03-25  Marcus Shawcroft  <marcus.shawcroft@arm.com>

	* elfnn-aarch64.c (_bfd_aarch64_resize_stubs): Adjust stub section
	size for initial branch.
	(elfNN_aarch64_build_stubs): Write initial branch.
	_bfd_aarch64_decode_(elfNN_aarch64_output_arch_local_syms): Write
	mapping symbol on initial branch.


 2015-03-25  Marcus Shawcroft  <marcus.shawcroft@arm.com>

	* ld-aarch64/erratum835769.d: Adjust for initial branch over stub
	section.
	* ld-aarch64/farcall-b.d: Likewise.
	* ld-aarch64/farcall-bl.d: Likewise.
	* ld-aarch64/farcall-back.d: Likewise.


diff --git a/bfd/elfnn-aarch64.c b/bfd/elfnn-aarch64.c
index 4ac4691..9b62a5e 100644
--- a/bfd/elfnn-aarch64.c
+++ b/bfd/elfnn-aarch64.c
@@ -3117,8 +3117,17 @@ _bfd_aarch64_resize_stubs (struct elf_aarch64_link_hash_table *htab)
     }
 
   bfd_hash_traverse (&htab->stub_hash_table, aarch64_size_one_stub, htab);
-}
 
+  for (section = htab->stub_bfd->sections;
+       section != NULL; section = section->next)
+    {
+      if (!strstr (section->name, STUB_SUFFIX))
+	continue;
+
+      if (section->size)
+	section->size += 4;
+    }
+}
 
 /* Determine and set the size of the stub section for a final link.
 
@@ -3482,6 +3491,9 @@ elfNN_aarch64_build_stubs (struct bfd_link_info *info)
       if (stub_sec->contents == NULL && size != 0)
 	return FALSE;
       stub_sec->size = 0;
+
+      bfd_putl32 (0x14000000 | (size >> 2), stub_sec->contents);
+      stub_sec->size += 4;
     }
 
   /* Build the stubs as directed by the stub hash table.  */
@@ -6501,6 +6513,10 @@ elfNN_aarch64_output_arch_local_syms (bfd *output_bfd,
 	  osi.sec_shndx = _bfd_elf_section_from_bfd_section
 	    (output_bfd, osi.sec->output_section);
 
+	  /* The first instruction in a stub is always a branch.  */
+	  if (!elfNN_aarch64_output_map_sym (&osi, AARCH64_MAP_INSN, 0))
+	    return FALSE;
+
 	  bfd_hash_traverse (&htab->stub_hash_table, aarch64_map_one_stub,
 			     &osi);
 	}
diff --git a/ld/testsuite/ld-aarch64/erratum835769.d b/ld/testsuite/ld-aarch64/erratum835769.d
index 1ff8d057..f3b0ed4 100644
--- a/ld/testsuite/ld-aarch64/erratum835769.d
+++ b/ld/testsuite/ld-aarch64/erratum835769.d
@@ -33,6 +33,7 @@ Disassembly of section .text:
 [ \t0-9a-f]+:[ \t]+aa0503e0[ \t]+mov[ \t]+x0, x5
 [ \t0-9a-f]+:[ \t]+d65f03c0[ \t]+ret
 
+[ \t0-9a-f]+:[ \t]+14000007[ \t]+b[ \t]+[0-9a-f]+ <__erratum_835769_veneer_0\+0x8>
 [0-9a-f]+ <__erratum_835769_veneer_2>:
 [ \t0-9a-f]+:[ \t]+9b031885[ \t]+madd[ \t]+x5, x4, x3, x6
 [ \t0-9a-f]+:[ \t0-9a-z]+[ \t]+b[ \t]+[0-9a-f]+ <a7str\+0x[0-9a-f]+>
diff --git a/ld/testsuite/ld-aarch64/farcall-b.d b/ld/testsuite/ld-aarch64/farcall-b.d
index f3cb5ef..c1a0c6f 100644
--- a/ld/testsuite/ld-aarch64/farcall-b.d
+++ b/ld/testsuite/ld-aarch64/farcall-b.d
@@ -8,12 +8,13 @@
 Disassembly of section .text:
 
 0000000000001000 <_start>:
- +1000:	14000002 	b	1008 <__bar_veneer>
+ +1000:	14000003 	b	100c <__bar_veneer>
  +1004:	d65f03c0 	ret
-0000000000001008 <__bar_veneer>:
-    1008:	90040010 	adrp	x16, 8001000 <bar>
-    100c:	91000210 	add	x16, x16, #0x0
-    1010:	d61f0200 	br	x16
+[ \t]+1008:[ \t]+14000007[ \t]+b[ \t]+1024 <__bar_veneer\+0x18>
+000000000000100c <__bar_veneer>:
+    100c:	90040010 	adrp	x16, 8001000 <bar>
+    1010:	91000210 	add	x16, x16, #0x0
+    1014:	d61f0200 	br	x16
 	...
 
 Disassembly of section .foo:
diff --git a/ld/testsuite/ld-aarch64/farcall-back.d b/ld/testsuite/ld-aarch64/farcall-back.d
index 9ff43b3..8b22360 100644
--- a/ld/testsuite/ld-aarch64/farcall-back.d
+++ b/ld/testsuite/ld-aarch64/farcall-back.d
@@ -9,64 +9,66 @@
 Disassembly of section .text:
 
 0000000000001000 <_start>:
-    1000:	14000412 	b	2048 <__bar1_veneer>
-    1004:	94000411 	bl	2048 <__bar1_veneer>
-    1008:	14000406 	b	2020 <__bar2_veneer>
-    100c:	94000405 	bl	2020 <__bar2_veneer>
-    1010:	14000408 	b	2030 <__bar3_veneer>
-    1014:	94000407 	bl	2030 <__bar3_veneer>
+    1000:	14000413 	b	204c <__bar1_veneer>
+    1004:	94000412 	bl	204c <__bar1_veneer>
+    1008:	14000407 	b	2024 <__bar2_veneer>
+    100c:	94000406 	bl	2024 <__bar2_veneer>
+    1010:	14000409 	b	2034 <__bar3_veneer>
+    1014:	94000408 	bl	2034 <__bar3_veneer>
     1018:	d65f03c0 	ret
 	...
 
 000000000000201c <_back>:
     201c:	d65f03c0 	ret
 
-0000000000002020 <__bar2_veneer>:
-    2020:	f07ffff0 	adrp	x16, 100001000 <bar1\+0x1000>
-    2024:	91002210 	add	x16, x16, #0x8
-    2028:	d61f0200 	br	x16
-    202c:	00000000 	.inst	0x00000000 ; undefined
+[ \t]+2020:[ \t]+14000013[ \t]+b[ \t]+206c <__bar1_veneer\+0x20>
+0000000000002024 <__bar2_veneer>:
+    2024:	f07ffff0 	adrp	x16, 100001000 <bar1\+0x1000>
+    2028:	91002210 	add	x16, x16, #0x8
+    202c:	d61f0200 	br	x16
+    2030:	00000000 	.inst	0x00000000 ; undefined
 
-0000000000002030 <__bar3_veneer>:
-    2030:	58000090 	ldr	x16, 2040 <__bar3_veneer\+0x10>
-    2034:	10000011 	adr	x17, 2034 <__bar3_veneer\+0x4>
-    2038:	8b110210 	add	x16, x16, x17
-    203c:	d61f0200 	br	x16
-    2040:	ffffffdc 	.word	0xffffffdc
-    2044:	00000000 	.word	0x00000000
+0000000000002034 <__bar3_veneer>:
+    2034:	58000090 	ldr	x16, 2044 <__bar3_veneer\+0x10>
+    2038:	10000011 	adr	x17, 2038 <__bar3_veneer\+0x4>
+    203c:	8b110210 	add	x16, x16, x17
+    2040:	d61f0200 	br	x16
+    2044:	ffffffd8 	.word	0xffffffd8
+    2048:	00000000 	.word	0x00000000
 
-0000000000002048 <__bar1_veneer>:
-    2048:	d07ffff0 	adrp	x16, 100000000 <bar1>
-    204c:	91000210 	add	x16, x16, #0x0
-    2050:	d61f0200 	br	x16
+000000000000204c <__bar1_veneer>:
+    204c:	d07ffff0 	adrp	x16, 100000000 <bar1>
+    2050:	91000210 	add	x16, x16, #0x0
+    2054:	d61f0200 	br	x16
 	...
 
 Disassembly of section .foo:
 
 0000000100000000 <bar1>:
    100000000:	d65f03c0 	ret
-   100000004:	14000805 	b	100002018 <___start_veneer>
+   100000004:	14000806 	b	10000201c <___start_veneer>
 	...
 
 0000000100001008 <bar2>:
    100001008:	d65f03c0 	ret
-   10000100c:	14000403 	b	100002018 <___start_veneer>
+   10000100c:	14000404 	b	10000201c <___start_veneer>
 	...
 
 0000000100002010 <bar3>:
    100002010:	d65f03c0 	ret
-   100002014:	14000007 	b	100002030 <___back_veneer>
+   100002014:	14000008 	b	100002034 <___back_veneer>
 
-0000000100002018 <___start_veneer>:
-   100002018:	58000090 	ldr	x16, 100002028 <___start_veneer\+0x10>
-   10000201c:	10000011 	adr	x17, 10000201c <___start_veneer\+0x4>
-   100002020:	8b110210 	add	x16, x16, x17
-   100002024:	d61f0200 	br	x16
-   100002028:	ffffefe4 	.word	0xffffefe4
-   10000202c:	fffffffe 	.word	0xfffffffe
+[ \t]+100002018:[ \t]+1400000d[ \t]+b[ \t]+10000204c <___back_veneer\+0x18>
+000000010000201c <___start_veneer>:
+   10000201c:	58000090 	ldr	x16, 10000202c <___start_veneer\+0x10>
+   100002020:	10000011 	adr	x17, 100002020 <___start_veneer\+0x4>
+   100002024:	8b110210 	add	x16, x16, x17
+   100002028:	d61f0200 	br	x16
+   10000202c:	ffffefe0 	.word	0xffffefe0
+   100002030:	fffffffe 	.word	0xfffffffe
 
-0000000100002030 <___back_veneer>:
-   100002030:	90800010 	adrp	x16, 2000 <_start\+0x1000>
-   100002034:	91007210 	add	x16, x16, #0x1c
-   100002038:	d61f0200 	br	x16
+0000000100002034 <___back_veneer>:
+   100002034:	90800010 	adrp	x16, 2000 <_start\+0x1000>
+   100002038:	91007210 	add	x16, x16, #0x1c
+   10000203c:	d61f0200 	br	x16
 	...
diff --git a/ld/testsuite/ld-aarch64/farcall-bl.d b/ld/testsuite/ld-aarch64/farcall-bl.d
index 2bdd2c4..78e94dc 100644
--- a/ld/testsuite/ld-aarch64/farcall-bl.d
+++ b/ld/testsuite/ld-aarch64/farcall-bl.d
@@ -8,13 +8,13 @@
 Disassembly of section .text:
 
 0000000000001000 <_start>:
- +1000:	94000002 	bl	1008 <__bar_veneer>
+ +1000:	94000003 	bl	100c <__bar_veneer>
  +1004:	d65f03c0 	ret
-
-0000000000001008 <__bar_veneer>:
-    1008:	90040010 	adrp	x16, 8001000 <bar>
-    100c:	91000210 	add	x16, x16, #0x0
-    1010:	d61f0200 	br	x16
+[ \t]+1008:[ \t]+14000007[ \t]+b[ \t]+1024 <__bar_veneer\+0x18>
+000000000000100c <__bar_veneer>:
+    100c:	90040010 	adrp	x16, 8001000 <bar>
+    1010:	91000210 	add	x16, x16, #0x0
+    1014:	d61f0200 	br	x16
 	...
 
 Disassembly of section .foo:
-- 
1.9.1




Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]