Add support for using the ADR alias in Thumb mode against nearby symbols.
authorNick Clifton <nickc@redhat.com>
Thu, 18 Jun 2015 09:23:16 +0000 (10:23 +0100)
committerNick Clifton <nickc@redhat.com>
Thu, 18 Jun 2015 09:23:16 +0000 (10:23 +0100)
PR gas/18541
gas * config/tc-arm.c (md_apply_fix): Add support for ADR in thumb
mode against a nearby symbol.

tests * gas/arm/thumb.s: Add test of ADR against a nearby symbol.
* gas/arm/thumb.d: Update expected output.
* gas/arm/thumb-eabi.d: Likewise.

gas/ChangeLog
gas/config/tc-arm.c
gas/testsuite/ChangeLog
gas/testsuite/gas/arm/thumb-eabi.d
gas/testsuite/gas/arm/thumb.d
gas/testsuite/gas/arm/thumb.s

index 00305e96f7e533e7d4f13aca9abf216b190c0864..0a1326e4241d3916c953c64166e9b14c1d5819f3 100644 (file)
@@ -1,3 +1,9 @@
+2015-06-18  Nick Clifton  <nickc@redhat.com>
+
+       PR gas/18541
+       * config/tc-arm.c (md_apply_fix): Add support for ADR in thumb
+       mode against a nearby symbol.
+
 2015-06-18  Nick Clifton  <nickc@redhat.com>
 
        PR gas/18481
index 9ccee400e8b5293c56f283928991e7c7cd7998c8..1793965785c32f868c8cf4bd00bdfa4b1e3083b1 100644 (file)
@@ -23158,6 +23158,45 @@ md_apply_fix (fixS *   fixP,
          }
        else if (rs == REG_PC || rs == REG_SP)
          {
+           /* PR gas/18541.  If the addition is for a defined symbol
+              within range of an ADR instruction then accept it.  */
+           if (subtract
+               && value == 4
+               && fixP->fx_addsy != NULL)
+             {
+               subtract = 0;
+
+               if (! S_IS_DEFINED (fixP->fx_addsy)
+                   || S_GET_SEGMENT (fixP->fx_addsy) != seg
+                   || S_IS_WEAK (fixP->fx_addsy))
+                 {
+                   as_bad_where (fixP->fx_file, fixP->fx_line,
+                                 _("address calculation needs a strongly defined nearby symbol"));
+                 }
+               else
+                 {
+                   offsetT v = fixP->fx_where + fixP->fx_frag->fr_address;
+
+                   /* Round up to the next 4-byte boundary.  */
+                   if (v & 3)
+                     v = (v + 3) & ~ 3;
+                   else
+                     v += 4;
+                   v = S_GET_VALUE (fixP->fx_addsy) - v;
+
+                   if (v & ~0x3fc)
+                     {
+                       as_bad_where (fixP->fx_file, fixP->fx_line,
+                                     _("symbol too far away"));
+                     }
+                   else
+                     {
+                       fixP->fx_done = 1;
+                       value = v;
+                     }
+                 }
+             }
+
            if (subtract || value & ~0x3fc)
              as_bad_where (fixP->fx_file, fixP->fx_line,
                            _("invalid immediate for address calculation (value = 0x%08lX)"),
index d929e689bec478c6af4f409319ce7a40d9b2b68f..64e8cd7b18d8a9c5fede0248075e3bd2163c6f6b 100644 (file)
@@ -1,3 +1,10 @@
+2015-06-18  Nick Clifton  <nickc@redhat.com>
+
+       PR gas/18541
+       * gas/arm/thumb.s: Add test of ADR against a nearby symbol.
+       * gas/arm/thumb.d: Update expected output.
+       * gas/arm/thumb-eabi.d: Likewise.
+
 2015-06-18  Nick Clifton  <nickc@redhat.com>
 
        PR gas/18481
index 19fc7972ba0f7d4d4c205dcad85f1846a777ac75..afe076ba2361f3c8c064e174a08bc8c07c4f90fa 100644 (file)
@@ -163,3 +163,8 @@ Disassembly of section \.text:
 0+942 <[^>]+> 4801             ldr     r0, \[pc, #4\]  ; \(0+948 <[^>]+>\)
 0+944 <[^>]+> 1c08             adds    r0, r1, #0
 0+946 <[^>]+> 46c0             nop                     ; \(mov r8, r8\)
+0+948 <[^>]+> a001             add     r0, pc, #4      ; \(adr r0, 00000950 <[^>]+>\)
+0+94a <[^>]+> a001             add     r0, pc, #4      ; \(adr r0, 00000950 <[^>]+>\)
+0+94c <[^>]+> a000             add     r0, pc, #0      ; \(adr r0, 00000950 <[^>]+>\)
+0+94e <[^>]+> 46c0             nop                     ; \(mov r8, r8\)
+#pass
index c928aaff436024a4d02c64005c0db010a71e3a53..65d007adf69342c160955a5958cddb711d0f8732 100644 (file)
@@ -163,3 +163,8 @@ Disassembly of section \.text:
 0+942 <[^>]+> 4801             ldr     r0, \[pc, #4\]  ; \(0+948 <[^>]+>\)
 0+944 <[^>]+> 1c08             adds    r0, r1, #0
 0+946 <[^>]+> 46c0             nop                     ; \(mov r8, r8\)
+0+948 <[^>]+> a001             add     r0, pc, #4      ; \(adr r0, 00000950 <[^>]+>\)
+0+94a <[^>]+> a001             add     r0, pc, #4      ; \(adr r0, 00000950 <[^>]+>\)
+0+94c <[^>]+> a000             add     r0, pc, #0      ; \(adr r0, 00000950 <[^>]+>\)
+0+94e <[^>]+> 46c0             nop                     ; \(mov r8, r8\)
+#pass
index a044bdfca589fcaf96f0e42e3d4d5f528872b6d2..3c759b35fde5041d127b364051647263a22fe396 100644 (file)
@@ -201,3 +201,13 @@ forwardonly:
 baz:
        mov     r0, r1
        nop
+
+       adr     r0, pr18541
+       adr     r0, pr18541
+       adr     r0, pr18541
+       nop
+       .align
+       .global pr18541
+pr18541:
+       .long   0
+