This is the mail archive of the
binutils@sourceware.org
mailing list for the binutils project.
[RFC PATCH] aarch64: ld: fix relaxations for ilp32 mode
- From: Yury Norov <ynorov at caviumnetworks dot com>
- To: <binutils at sourceware dot org>
- Cc: Yury Norov <ynorov at caviumnetworks dot com>
- Date: Sat, 14 Jan 2017 16:18:10 +0530
- Subject: [RFC PATCH] aarch64: ld: fix relaxations for ilp32 mode
- Authentication-results: sourceware.org; auth=none
- Authentication-results: spf=none (sender IP is ) smtp.mailfrom=Yuri dot Norov at caviumnetworks dot com;
- Spamdiagnosticmetadata: NSPM
- Spamdiagnosticoutput: 1:99
Hi all,
This patch continues the work of replacing 64-bit registers, offsets etc with
32-bit ones in elfNN_aarch64_tls_relax(). It doesn't fix any test I have tried,
but it's generally correct, and I think that it should be applied.
I also added new tests for ilp32 mode, and the problem is that some fail. So I'd
like to ask for help here.
Namely, 3 new tests are failed. tls-relax-large-desc-ie-ilp32 and
tls-relax-large-desc-le-ilp32 fail due to error "cannot represent
BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format", and
test tls-desc-ie-ilp32 fails due to weird "undefined reference to `v2".
If my understanding is correct, this error is because GAS cannot translate
assembler commands to machine codes properly. If so, it may happen with some real
program one day.
It may also be my misunderstanding on how gas/ld work.
Anyway, please give me any clue on this errors, and how to handle it.
Yury
Error logs:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s: Assembler message s:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:14: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:16: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:21: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s: Assembler message s:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:14: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:16: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:21: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
failed with: </home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s: Ass embler messages:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:14: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:16: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie.s:21: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
>
FAIL: ld-aarch64/tls-relax-large-desc-ie-ilp32
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s: Assembler messages:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:11: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:15: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:20: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s: Assembler messages:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:11: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:15: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:20: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
failed with: </home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s: Assembler messages:
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:11: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G1 relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:12: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:13: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_LDR relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:15: Error: cannot
represent BFD_RELOC_AARCH64_TLSDESC_ADD relocation in this object file format
/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-relax-large-desc-le.s:20: Error: cannot
represent BFD_RELOC_64_PCREL relocation in this object file format
>
FAIL: ld-aarch64/tls-relax-large-desc-le-ilp32
/home/yury/work/glibc-img/binutils.src/build/ld/../gas/as-new -mabi=ilp32 -o tmpdir/tls-desc-ie.o /home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-desc-ie.s
Executing on host: sh -c {/home/yury/work/glibc-img/binutils.src/build/ld/../gas/as-new -mabi=ilp32 -o tmpdir/tls-desc-ie.o /home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64/tls-desc-ie.s 2>&1} /dev/null ld.tmp (timeout = 300)
spawn [open ...]
./ld-new -z norelro -L/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64 -m aarch64linux32 -T relocs-ilp32.ld -e0 -o tmpdir/dump tmpdir/tls-desc-ie.o
Executing on host: sh -c {./ld-new -z norelro -L/home/yury/work/glibc-img/binutils.src/ld/testsuite/ld-aarch64 -m aarch64linux32 -T relocs-ilp32.ld -e0 -o tmpdir/dump tmpdir/tls-desc-ie.o 2>&1} /dev/null ld.tmp (timeout = 300)
spawn [open ...]
tmpdir/tls-desc-ie.o:(.text+0x0): undefined reference to `v2'
tmpdir/tls-desc-ie.o:(.text+0x4): undefined reference to `v2'
failed with: <tmpdir/tls-desc-ie.o:(.text+0x0): undefined reference to `v2'
tmpdir/tls-desc-ie.o:(.text+0x4): undefined reference to `v2'>, no expected output
tmpdir/tls-desc-ie.o:(.text+0x0): undefined reference to `v2'
tmpdir/tls-desc-ie.o:(.text+0x4): undefined reference to `v2'
FAIL: ld-aarch64/tls-desc-ie-ilp32
---
bfd/elfnn-aarch64.c | 149 ++++++++++++++++-----
ld/testsuite/ld-aarch64/aarch64-elf.exp | 16 ++-
ld/testsuite/ld-aarch64/tls-desc-ie-ilp32.d | 37 +++++
ld/testsuite/ld-aarch64/tls-relax-all-ilp32.d | 40 ++++++
ld/testsuite/ld-aarch64/tls-relax-gd-le-ilp32.d | 10 ++
.../ld-aarch64/tls-relax-gdesc-le-2-ilp32.d | 19 +++
ld/testsuite/ld-aarch64/tls-relax-gdesc-le-ilp32.d | 13 ++
ld/testsuite/ld-aarch64/tls-relax-ie-le-2-ilp32.d | 18 +++
ld/testsuite/ld-aarch64/tls-relax-ie-le-3-ilp32.d | 10 ++
ld/testsuite/ld-aarch64/tls-relax-ie-le-ilp32.d | 10 ++
.../ld-aarch64/tls-relax-large-desc-ie-ilp32.d | 20 +++
.../ld-aarch64/tls-relax-large-desc-le-ilp32.d | 19 +++
ld/testsuite/ld-aarch64/tls-tiny-desc-ie-ilp32.d | 12 ++
ld/testsuite/ld-aarch64/tls-tiny-desc-le-ilp32.d | 12 ++
ld/testsuite/ld-aarch64/tls-tiny-gd-ie-ilp32.d | 12 ++
ld/testsuite/ld-aarch64/tls-tiny-gd-le-ilp32.d | 12 ++
16 files changed, 372 insertions(+), 37 deletions(-)
create mode 100644 ld/testsuite/ld-aarch64/tls-desc-ie-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-all-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-gd-le-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-gdesc-le-2-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-gdesc-le-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-ie-le-2-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-ie-le-3-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-ie-le-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-large-desc-ie-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-relax-large-desc-le-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-tiny-desc-ie-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-tiny-desc-le-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-tiny-gd-ie-ilp32.d
create mode 100644 ld/testsuite/ld-aarch64/tls-tiny-gd-le-ilp32.d
diff --git a/bfd/elfnn-aarch64.c b/bfd/elfnn-aarch64.c
index d6cc2a0..820e2f8 100644
--- a/bfd/elfnn-aarch64.c
+++ b/bfd/elfnn-aarch64.c
@@ -5644,11 +5644,16 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
if (is_local)
{
/* GD->LE relaxation:
- adrp x0, :tlsgd:var => movz x0, :tprel_g1:var
+ adrp x0, :tlsgd:var => movz R0, :tprel_g1:var
or
- adrp x0, :tlsdesc:var => movz x0, :tprel_g1:var
- */
+ adrp x0, :tlsdesc:var => movz R0, :tprel_g1:var
+
+ Where R is x for LP64, and x for ilp32. */
+#if ARCH_SIZE == 64
bfd_putl32 (0xd2a00000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x52a00000, contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
}
else
@@ -5669,11 +5674,12 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
if (is_local)
{
/* Tiny TLSDESC->LE relaxation:
- ldr x1, :tlsdesc:var => movz x0, #:tprel_g1:var
- adr x0, :tlsdesc:var => movk x0, #:tprel_g0_nc:var
+ ldr x1, :tlsdesc:var => movz R0, #:tprel_g1:var
+ adr x0, :tlsdesc:var => movk R0, #:tprel_g0_nc:var
.tlsdesccall var
blr x1 => nop
- */
+
+ Where R is x for LP64, and x for ilp32. */
BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (TLSDESC_ADR_PREL21));
BFD_ASSERT (ELFNN_R_TYPE (rel[2].r_info) == AARCH64_R (TLSDESC_CALL));
@@ -5681,8 +5687,13 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
AARCH64_R (TLSLE_MOVW_TPREL_G0_NC));
rel[2].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
+#if ARCH_SIZE == 64
bfd_putl32 (0xd2a00000, contents + rel->r_offset);
bfd_putl32 (0xf2800000, contents + rel->r_offset + 4);
+#else
+ bfd_putl32 (0x52a00000, contents + rel->r_offset);
+ bfd_putl32 (0x72800000, contents + rel->r_offset + 4);
+#endif
bfd_putl32 (INSN_NOP, contents + rel->r_offset + 8);
return bfd_reloc_continue;
}
@@ -5700,7 +5711,11 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
rel[2].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
+#if ARCH_SIZE == 64
bfd_putl32 (0x58000000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x18000000, contents + rel->r_offset);
+#endif
bfd_putl32 (INSN_NOP, contents + rel->r_offset + 4);
bfd_putl32 (INSN_NOP, contents + rel->r_offset + 8);
return bfd_reloc_continue;
@@ -5711,17 +5726,22 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
{
/* Tiny GD->LE relaxation:
adr x0, :tlsgd:var => mrs x1, tpidr_el0
- bl __tls_get_addr => add x0, x1, #:tprel_hi12:x, lsl #12
- nop => add x0, x0, #:tprel_lo12_nc:x
- */
+ bl __tls_get_addr => add R0, R1, #:tprel_hi12:x, lsl #12
+ nop => add R0, R0, #:tprel_lo12_nc:x
+
+ Where R is x for LP64, and x for ilp32. */
/* First kill the tls_get_addr reloc on the bl instruction. */
BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
bfd_putl32 (0xd53bd041, contents + rel->r_offset + 0);
+#if ARCH_SIZE == 64
bfd_putl32 (0x91400020, contents + rel->r_offset + 4);
bfd_putl32 (0x91000000, contents + rel->r_offset + 8);
-
+#else
+ bfd_putl32 (0x11400020, contents + rel->r_offset + 4);
+ bfd_putl32 (0x11000000, contents + rel->r_offset + 8);
+#endif
rel[1].r_info = ELFNN_R_INFO (ELFNN_R_SYM (rel->r_info),
AARCH64_R (TLSLE_ADD_TPREL_LO12_NC));
rel[1].r_offset = rel->r_offset + 8;
@@ -5736,18 +5756,24 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
else
{
/* Tiny GD->IE relaxation:
- adr x0, :tlsgd:var => ldr x0, :gottprel:var
+ adr x0, :tlsgd:var => ldr R0, :gottprel:var
bl __tls_get_addr => mrs x1, tpidr_el0
- nop => add x0, x0, x1
- */
+ nop => add R0, R0, R1
+
+ Where R is x for LP64, and x for ilp32. */
/* First kill the tls_get_addr reloc on the bl instruction. */
BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
+#if ARCH_SIZE == 64
bfd_putl32 (0x58000000, contents + rel->r_offset);
- bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
bfd_putl32 (0x8b000020, contents + rel->r_offset + 8);
+#else
+ bfd_putl32 (0x18000000, contents + rel->r_offset);
+ bfd_putl32 (0x0b000020, contents + rel->r_offset + 8);
+#endif
+ bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
return bfd_reloc_continue;
}
@@ -5805,17 +5831,27 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
{
/* GD->LE relaxation:
ldr xd, [x0, #:tlsdesc_lo12:var] => movk x0, :tprel_g0_nc:var
- */
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
+#if ARCH_SIZE == 64
bfd_putl32 (0xf2800000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x72800000, contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
}
else
{
/* GD->IE relaxation:
- ldr xd, [x0, #:tlsdesc_lo12:var] => ldr x0, [x0, #:gottprel_lo12:var]
- */
+ ldr xd, [x0, #:tlsdesc_lo12:var] => ldr R0, [x0, #:gottprel_lo12:var]
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
insn = bfd_getl32 (contents + rel->r_offset);
+#if ARCH_SIZE == 64
insn &= 0xffffffe0;
+#else
+ insn &= 0xbfffffe0;
+#endif
bfd_putl32 (insn, contents + rel->r_offset);
return bfd_reloc_continue;
}
@@ -5824,18 +5860,24 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
if (is_local)
{
/* GD->LE relaxation
- add x0, #:tlsgd_lo12:var => movk x0, :tprel_g0_nc:var
+ add x0, #:tlsgd_lo12:var => movk R0, :tprel_g0_nc:var
bl __tls_get_addr => mrs x1, tpidr_el0
- nop => add x0, x1, x0
- */
+ nop => add R0, R1, R0
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
/* First kill the tls_get_addr reloc on the bl instruction. */
BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
+#if ARCH_SIZE == 64
bfd_putl32 (0xf2800000, contents + rel->r_offset);
- bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
bfd_putl32 (0x8b000020, contents + rel->r_offset + 8);
+#else
+ bfd_putl32 (0x72800000, contents + rel->r_offset);
+ bfd_putl32 (0x0b000020, contents + rel->r_offset + 8);
+#endif
+ bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
return bfd_reloc_continue;
}
else
@@ -5881,70 +5923,105 @@ elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
if (is_local)
{
/* GD->LE relaxation:
- ldr xd, [gp, xn] => movk x0, #:tprel_g0_nc:var
- */
+ ldr xd, [gp, xn] => movk R0, #:tprel_g0_nc:var
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
+#if ARCH_SIZE == 64
bfd_putl32 (0xf2800000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x72800000, contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
}
else
{
/* GD->IE relaxation:
- ldr xd, [gp, xn] => ldr x0, [gp, xn]
- */
+ ldr xd, [gp, xn] => ldr R0, [gp, xn]
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
insn = bfd_getl32 (contents + rel->r_offset);
+#if ARCH_SIZE == 64
insn &= 0xffffffe0;
+#else
+ insn &= 0xbfffffe0;
+#endif
bfd_putl32 (insn, contents + rel->r_offset);
return bfd_reloc_ok;
}
case BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC:
/* GD->LE relaxation:
- movk xd, #:tlsdesc_off_g0_nc:var => movk x0, #:tprel_g1_nc:var, lsl #16
+ movk xd, #:tlsdesc_off_g0_nc:var => movk R0, #:tprel_g1_nc:var, lsl #16
GD->IE relaxation:
- movk xd, #:tlsdesc_off_g0_nc:var => movk xd, #:gottprel_g0_nc:var
- */
+ movk xd, #:tlsdesc_off_g0_nc:var => movk Rd, #:gottprel_g0_nc:var
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
if (is_local)
+#if ARCH_SIZE == 64
bfd_putl32 (0xf2a00000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x72a00000, contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
case BFD_RELOC_AARCH64_TLSDESC_OFF_G1:
if (is_local)
{
/* GD->LE relaxation:
- movz xd, #:tlsdesc_off_g1:var => movz x0, #:tprel_g2:var, lsl #32
- */
+ movz xd, #:tlsdesc_off_g1:var => movz R0, #:tprel_g2:var, lsl #32
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
+#if ARCH_SIZE == 64
bfd_putl32 (0xd2c00000, contents + rel->r_offset);
+#else
+ bfd_putl32 (0x52800000, contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
}
else
{
/* GD->IE relaxation:
- movz xd, #:tlsdesc_off_g1:var => movz xd, #:gottprel_g1:var, lsl #16
- */
+ movz xd, #:tlsdesc_off_g1:var => movz Rd, #:gottprel_g1:var, lsl #16
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
insn = bfd_getl32 (contents + rel->r_offset);
+#if ARCH_SIZE == 64
bfd_putl32 (0xd2a00000 | (insn & 0x1f), contents + rel->r_offset);
+#else
+ bfd_putl32 (0x52a00000 | (insn & 0x1f), contents + rel->r_offset);
+#endif
return bfd_reloc_continue;
}
case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
/* IE->LE relaxation:
- adrp xd, :gottprel:var => movz xd, :tprel_g1:var
- */
+ adrp xd, :gottprel:var => movz Rd, :tprel_g1:var
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
if (is_local)
{
insn = bfd_getl32 (contents + rel->r_offset);
+#if ARCH_SIZE == 64
bfd_putl32 (0xd2a00000 | (insn & 0x1f), contents + rel->r_offset);
+#else
+ bfd_putl32 (0x52a00000 | (insn & 0x1f), contents + rel->r_offset);
+#endif
}
return bfd_reloc_continue;
case BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC:
/* IE->LE relaxation:
- ldr xd, [xm, #:gottprel_lo12:var] => movk xd, :tprel_g0_nc:var
- */
+ ldr xd, [xm, #:gottprel_lo12:var] => movk Rd, :tprel_g0_nc:var
+
+ Where R is x for lp64 mode, and w for ilp32 mode. */
if (is_local)
{
insn = bfd_getl32 (contents + rel->r_offset);
+#if ARCH_SIZE == 64
bfd_putl32 (0xf2800000 | (insn & 0x1f), contents + rel->r_offset);
+#else
+ bfd_putl32 (0x72800000 | (insn & 0x1f), contents + rel->r_offset);
+#endif
}
return bfd_reloc_continue;
diff --git a/ld/testsuite/ld-aarch64/aarch64-elf.exp b/ld/testsuite/ld-aarch64/aarch64-elf.exp
index 8fba231..30a5e56 100644
--- a/ld/testsuite/ld-aarch64/aarch64-elf.exp
+++ b/ld/testsuite/ld-aarch64/aarch64-elf.exp
@@ -213,35 +213,49 @@ run_dump_test "farcall-b-section"
run_dump_test "farcall-bl-section"
run_dump_test "tls-relax-all"
+run_dump_test "tls-relax-all-ilp32"
run_dump_test "tls-relax-gd-le"
+run_dump_test "tls-relax-gd-le-ilp32"
run_dump_test "tls-relax-gdesc-le"
-run_dump_test "tls-relax-gd-ie-ilp32"
+run_dump_test "tls-relax-gdesc-le-ilp32"
run_dump_test "tls-relax-gd-ie"
+run_dump_test "tls-relax-gd-ie-ilp32"
run_dump_test_lp64 "tls-relax-large-gd-ie"
run_dump_test_lp64 "tls-relax-large-gd-ie-be"
run_dump_test_lp64 "tls-relax-large-gd-le"
run_dump_test_lp64 "tls-relax-large-gd-le-be"
run_dump_test_lp64 "tls-relax-large-desc-ie"
+run_dump_test "tls-relax-large-desc-ie-ilp32"
run_dump_test_lp64 "tls-relax-large-desc-ie-be"
run_dump_test_lp64 "tls-relax-large-desc-le"
+run_dump_test "tls-relax-large-desc-le-ilp32"
run_dump_test_lp64 "tls-relax-large-desc-le-be"
run_dump_test "tls-relax-gdesc-ie"
run_dump_test "tls-relax-ie-le"
+run_dump_test "tls-relax-ie-le-ilp32"
run_dump_test "tls-relax-ld-le-small"
run_dump_test "tls-relax-ld-le-small-ilp32"
run_dump_test "tls-relax-ld-le-tiny"
run_dump_test "tls-relax-ld-le-tiny-ilp32"
run_dump_test "tls-desc-ie"
+run_dump_test "tls-desc-ie-ilp32"
run_dump_test "tls-relax-gdesc-ie-2"
run_dump_test "tls-relax-gdesc-le-2"
+run_dump_test "tls-relax-gdesc-le-2-ilp32"
run_dump_test "tls-relax-ie-le-2"
+run_dump_test "tls-relax-ie-le-2-ilp32"
run_dump_test "tls-relax-ie-le-3"
+run_dump_test "tls-relax-ie-le-3-ilp32"
run_dump_test "tls-tiny-gd"
run_dump_test "tls-tiny-gd-ie"
+run_dump_test "tls-tiny-gd-ie-ilp32"
run_dump_test "tls-tiny-gd-le"
+run_dump_test "tls-tiny-gd-le-ilp32"
run_dump_test "tls-tiny-desc"
run_dump_test "tls-tiny-desc-ie"
+run_dump_test "tls-tiny-desc-ie-ilp32"
run_dump_test "tls-tiny-desc-le"
+run_dump_test "tls-tiny-desc-le-ilp32"
run_dump_test "tls-tiny-ie"
run_dump_test_lp64 "tls-large-ie"
run_dump_test_lp64 "tls-large-ie-be"
diff --git a/ld/testsuite/ld-aarch64/tls-desc-ie-ilp32.d b/ld/testsuite/ld-aarch64/tls-desc-ie-ilp32.d
new file mode 100644
index 0000000..ca8e166
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-desc-ie-ilp32.d
@@ -0,0 +1,37 @@
+#source: tls-desc-ie.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: 90000080 adrp x0, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10004: 91004000 add x0, x0, #0x10
+ +10008: 94000016 bl 10060 <.*>
+ +1000c: d503201f nop
+ +10010: 90000080 adrp x0, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10014: f9400400 ldr x0, \[x0, #8\]
+ +10018: d503201f nop
+ +1001c: d503201f nop
+ +10020: d53bd041 mrs x1, tpidr_el0
+ +10024: 8b000020 add x0, x1, x0
+ +10028: d53bd042 mrs x2, tpidr_el0
+ +1002c: 90000080 adrp x0, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10030: f9400400 ldr x0, \[x0, #8\]
+ +10034: 8b000040 add x0, x2, x0
+ +10038: b9400000 ldr w0, \[x0\]
+ +1003c: 0b000020 add w0, w1, w0
+
+Disassembly of section .plt:
+
+0000000000010040 <.plt>:
+ +10040: a9bf7bf0 stp x16, x30, \[sp, #-16\]!
+ +10044: 90000090 adrp x16, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10048: f9401a11 ldr x17, \[x16, #48\]
+ +1004c: 9100c210 add x16, x16, #0x30
+ +10050: d61f0220 br x17
+ +10054: d503201f nop
+ +10058: d503201f nop
+ +1005c: d503201f nop
+ +10060: 90000090 adrp x16, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10064: f9401e11 ldr x17, \[x16, #56\]
+ +10068: 9100e210 add x16, x16, #0x38
+ +1006c: d61f0220 br x17
diff --git a/ld/testsuite/ld-aarch64/tls-relax-all-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-all-ilp32.d
new file mode 100644
index 0000000..1cb4ef4
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-all-ilp32.d
@@ -0,0 +1,40 @@
+#source: tls-relax-all.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: a9bf7bfd stp x29, x30, \[sp, #-16\]!
+ +10004: 910003fd mov x29, sp
+ +10008: 90000080 adrp x0, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +1000c: b9400400 ldr w0, \[x0, #4\]
+ +10010: d503201f nop
+ +10014: d503201f nop
+ +10018: d53bd041 mrs x1, tpidr_el0
+ +1001c: 8b000020 add x0, x1, x0
+ +10020: b9400001 ldr w1, \[x0\]
+ +10024: 52a00000 movz w0, #0x0, lsl #16
+ +10028: 72800180 movk w0, #0xc
+ +1002c: d503201f nop
+ +10030: d503201f nop
+ +10034: d53bd042 mrs x2, tpidr_el0
+ +10038: 8b000040 add x0, x2, x0
+ +1003c: b9400000 ldr w0, \[x0\]
+ +10040: 0b000021 add w1, w1, w0
+ +10044: 90000080 adrp x0, 20000 <_GLOBAL_OFFSET_TABLE_>
+ +10048: b9400800 ldr w0, \[x0, #8\]
+ +1004c: d53bd041 mrs x1, tpidr_el0
+ +10050: 0b000020 add w0, w1, w0
+ +10054: b9400000 ldr w0, \[x0\]
+ +10058: 0b000021 add w1, w1, w0
+ +1005c: 52a00000 movz w0, #0x0, lsl #16
+ +10060: 72800280 movk w0, #0x14
+ +10064: d53bd041 mrs x1, tpidr_el0
+ +10068: 0b000020 add w0, w1, w0
+ +1006c: b9400000 ldr w0, \[x0\]
+ +10070: 0b000021 add w1, w1, w0
+ +10074: d53bd042 mrs x2, tpidr_el0
+ +10078: 52a00000 movz w0, #0x0, lsl #16
+ +1007c: 72800300 movk w0, #0x18
+ +10080: 8b000040 add x0, x2, x0
+ +10084: b9400000 ldr w0, \[x0\]
+ +10088: 0b000020 add w0, w1, w0
diff --git a/ld/testsuite/ld-aarch64/tls-relax-gd-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-gd-le-ilp32.d
new file mode 100644
index 0000000..dd91cb4
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-gd-le-ilp32.d
@@ -0,0 +1,10 @@
+#source: tls-relax-gd-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: 52a00000 movz w0, #0x0, lsl #16
+ +10004: 72800100 movk w0, #0x8
+ +10008: d53bd041 mrs x1, tpidr_el0
+ +1000c: 0b000020 add w0, w1, w0
+ +10010: b9400000 ldr w0, \[x0\]
diff --git a/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-2-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-2-ilp32.d
new file mode 100644
index 0000000..903b0b4
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-2-ilp32.d
@@ -0,0 +1,19 @@
+#source: tls-relax-gdesc-le-2.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: 52a00000 movz w0, #0x0, lsl #16
+ +10004: d503201f nop
+ +10008: d503201f nop
+ +1000c: 72800100 movk w0, #0x8
+ +10010: d503201f nop
+ +10014: d503201f nop
+ +10018: d503201f nop
+ +1001c: d503201f nop
+ +10020: d503201f nop
+ +10024: d503201f nop
+ +10028: d503201f nop
+ +1002c: d53bd041 mrs x1, tpidr_el0
+ +10030: 8b000020 add x0, x1, x0
+ +10034: b9400000 ldr w0, \[x0\]
diff --git a/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-ilp32.d
new file mode 100644
index 0000000..331c1c9
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-gdesc-le-ilp32.d
@@ -0,0 +1,13 @@
+#source: tls-relax-gdesc-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: 52a00000 movz w0, #0x0, lsl #16
+ +10004: 72800100 movk w0, #0x8
+ +10008: d503201f nop
+ +1000c: d503201f nop
+ +10010: d53bd041 mrs x1, tpidr_el0
+ +10014: 8b000020 add x0, x1, x0
+ +10018: b9400000 ldr w0, \[x0\]
+
diff --git a/ld/testsuite/ld-aarch64/tls-relax-ie-le-2-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-ie-le-2-ilp32.d
new file mode 100644
index 0000000..71ee72c
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-ie-le-2-ilp32.d
@@ -0,0 +1,18 @@
+#source: tls-relax-ie-le-2.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: d53bd041 mrs x1, tpidr_el0
+ +10004: d503201f nop
+ +10008: d503201f nop
+ +1000c: 52a00000 movz w0, #0x0, lsl #16
+ +10010: d503201f nop
+ +10014: d503201f nop
+ +10018: d503201f nop
+ +1001c: 72800100 movk w0, #0x8
+ +10020: d503201f nop
+ +10024: 8b000020 add x0, x1, x0
+ +10028: d503201f nop
+ +1002c: d503201f nop
+ +10030: b9400000 ldr w0, \[x0\]
diff --git a/ld/testsuite/ld-aarch64/tls-relax-ie-le-3-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-ie-le-3-ilp32.d
new file mode 100644
index 0000000..e0bc05d
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-ie-le-3-ilp32.d
@@ -0,0 +1,10 @@
+#source: tls-relax-ie-le-3.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: d53bd042 mrs x2, tpidr_el0
+ +10004: 52a0000f movz w15, #0x0, lsl #16
+ +10008: 7280010f movk w15, #0x8
+ +1000c: 8b0f004f add x15, x2, x15
+ +10010: b94001e0 ldr w0, \[x15\]
diff --git a/ld/testsuite/ld-aarch64/tls-relax-ie-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-ie-le-ilp32.d
new file mode 100644
index 0000000..ede3d8c
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-ie-le-ilp32.d
@@ -0,0 +1,10 @@
+#source: tls-relax-ie-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+ +10000: d53bd041 mrs x1, tpidr_el0
+ +10004: 52a00000 movz w0, #0x0, lsl #16
+ +10008: 72800100 movk w0, #0x8
+ +1000c: 8b000020 add x0, x1, x0
+ +10010: b9400000 ldr w0, \[x0\]
diff --git a/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie-ilp32.d
new file mode 100644
index 0000000..27ba53a
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-large-desc-ie-ilp32.d
@@ -0,0 +1,20 @@
+#source: tls-relax-large-desc-ie.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#notarget: aarch64_be-*-*
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+0000000000010000 <test>:
+ +10000: 58000101 ldr x1, 10020 \<test\+0x20\>
+ +10004: 100000e2 adr x2, 10020 \<test\+0x20\>
+ +10008: 8b020032 add x18, x1, x2
+ +1000c: d2a00000 movz x0, #0x0, lsl #16
+ +10010: f2800100 movk x0, #0x8
+ +10014: f8606a40 ldr x0, \[x18, x0\]
+ +10018: d503201f nop
+ +1001c: d503201f nop
+ +10020: 0000ffe0 .word 0x0000ffe0
+ +10024: 00000000 .word 0x00000000
diff --git a/ld/testsuite/ld-aarch64/tls-relax-large-desc-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-relax-large-desc-le-ilp32.d
new file mode 100644
index 0000000..ffab773
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-relax-large-desc-le-ilp32.d
@@ -0,0 +1,19 @@
+#source: tls-relax-large-desc-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+0000000000010000 <test>:
+ +10000: 58000101 ldr x1, 10020 \<test\+0x20\>
+ +10004: 100000e2 adr x2, 10020 \<test\+0x20\>
+ +10008: 8b020032 add x18, x1, x2
+ +1000c: d2c00000 movz x0, #0x0, lsl #32
+ +10010: f2a00000 movk x0, #0x0, lsl #16
+ +10014: f2800200 movk x0, #0x10
+ +10018: d503201f nop
+ +1001c: d503201f nop
+ +10020: 0000ffe0 .word 0x0000ffe0
+ +10024: 00000000 .word 0x00000000
diff --git a/ld/testsuite/ld-aarch64/tls-tiny-desc-ie-ilp32.d b/ld/testsuite/ld-aarch64/tls-tiny-desc-ie-ilp32.d
new file mode 100644
index 0000000..ebbaf85
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-tiny-desc-ie-ilp32.d
@@ -0,0 +1,12 @@
+#source: tls-tiny-desc-ie.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+00010000 \<test\>:
+ +10000: 18080020 ldr w0, 20004 \<_GLOBAL_OFFSET_TABLE_\+0x4\>
+ +10004: d503201f nop
+ +10008: d503201f nop
diff --git a/ld/testsuite/ld-aarch64/tls-tiny-desc-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-tiny-desc-le-ilp32.d
new file mode 100644
index 0000000..79a6f5c
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-tiny-desc-le-ilp32.d
@@ -0,0 +1,12 @@
+#source: tls-tiny-desc-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+00010000 \<test\>:
+ +10000: 52a00000 movz w0, #0x0, lsl #16
+ +10004: 72800100 movk w0, #0x8
+ +10008: d503201f nop
diff --git a/ld/testsuite/ld-aarch64/tls-tiny-gd-ie-ilp32.d b/ld/testsuite/ld-aarch64/tls-tiny-gd-ie-ilp32.d
new file mode 100644
index 0000000..1ea6110
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-tiny-gd-ie-ilp32.d
@@ -0,0 +1,12 @@
+#source: tls-tiny-gd-ie.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+00010000 \<test\>:
+ +10000: 18080020 ldr w0, 20004 \<_GLOBAL_OFFSET_TABLE_\+0x4\>
+ +10004: d53bd041 mrs x1, tpidr_el0
+ +10008: 0b000020 add w0, w1, w0
diff --git a/ld/testsuite/ld-aarch64/tls-tiny-gd-le-ilp32.d b/ld/testsuite/ld-aarch64/tls-tiny-gd-le-ilp32.d
new file mode 100644
index 0000000..5213a04
--- /dev/null
+++ b/ld/testsuite/ld-aarch64/tls-tiny-gd-le-ilp32.d
@@ -0,0 +1,12 @@
+#source: tls-tiny-gd-le.s
+#as: -mabi=ilp32
+#ld: -m [aarch64_choose_ilp32_emul] -T relocs-ilp32.ld -e0
+#objdump: -dr
+#...
+
+Disassembly of section .text:
+
+00010000 \<test\>:
+ +10000: d53bd041 mrs x1, tpidr_el0
+ +10004: 11400020 add w0, w1, #0x0, lsl #12
+ +10008: 11002000 add w0, w0, #0x8
--
2.7.4