[lld] [lld] Add support for relocations in x86_64 objects on Arm64EC targets. (PR #69098)

Jacek Caban via llvm-commits llvm-commits at lists.llvm.org
Mon Oct 16 11:49:29 PDT 2023


https://github.com/cjacek updated https://github.com/llvm/llvm-project/pull/69098

>From 195029f730ea0a444c940039555d2c336d21281d Mon Sep 17 00:00:00 2001
From: Jacek Caban <jacek at codeweavers.com>
Date: Fri, 21 Apr 2023 00:39:41 +0200
Subject: [PATCH] [lld] Add support for relocations in x86_64 objects on
 Arm64EC targets.

Since EC targets may combine various object types, we need to pick relocation format based on chunk type instead of global config.
---
 lld/COFF/Chunks.cpp              |  4 ++--
 lld/COFF/Chunks.h                |  2 ++
 lld/test/COFF/arm64ec-reloc.test | 37 ++++++++++++++++++++++++++++++++
 3 files changed, 41 insertions(+), 2 deletions(-)
 create mode 100644 lld/test/COFF/arm64ec-reloc.test

diff --git a/lld/COFF/Chunks.cpp b/lld/COFF/Chunks.cpp
index e17b64df869fe88..4e845afa8947a5f 100644
--- a/lld/COFF/Chunks.cpp
+++ b/lld/COFF/Chunks.cpp
@@ -437,7 +437,7 @@ void SectionChunk::applyRelocation(uint8_t *off,
   // Compute the RVA of the relocation for relative relocations.
   uint64_t p = rva + rel.VirtualAddress;
   uint64_t imageBase = file->ctx.config.imageBase;
-  switch (file->ctx.config.machine) {
+  switch (getMachine()) {
   case AMD64:
     applyRelX64(off, rel.Type, os, s, p, imageBase);
     break;
@@ -551,7 +551,7 @@ static uint8_t getBaserelType(const coff_relocation &rel,
 // Only called when base relocation is enabled.
 void SectionChunk::getBaserels(std::vector<Baserel> *res) {
   for (const coff_relocation &rel : getRelocs()) {
-    uint8_t ty = getBaserelType(rel, file->ctx.config.machine);
+    uint8_t ty = getBaserelType(rel, getMachine());
     if (ty == IMAGE_REL_BASED_ABSOLUTE)
       continue;
     Symbol *target = file->getSymbol(rel.SymbolTableIndex);
diff --git a/lld/COFF/Chunks.h b/lld/COFF/Chunks.h
index 3d605e6ab10c8c8..d14a258fc81e121 100644
--- a/lld/COFF/Chunks.h
+++ b/lld/COFF/Chunks.h
@@ -219,6 +219,8 @@ class SectionChunk final : public Chunk {
   ArrayRef<uint8_t> getContents() const;
   void writeTo(uint8_t *buf) const;
 
+  MachineTypes getMachine() const { return file->getMachineType(); }
+
   // Defend against unsorted relocations. This may be overly conservative.
   void sortRelocations();
 
diff --git a/lld/test/COFF/arm64ec-reloc.test b/lld/test/COFF/arm64ec-reloc.test
new file mode 100644
index 000000000000000..3060891bfe02e87
--- /dev/null
+++ b/lld/test/COFF/arm64ec-reloc.test
@@ -0,0 +1,37 @@
+REQUIRES: aarch64, x86
+RUN: split-file %s %t.dir && cd %t.dir
+
+Link a mix of ARM64EC and x86_64 data and check that relocations work.
+
+RUN: llvm-mc -filetype=obj -triple=arm64ec-windows arm64ec-data-sym.s -o arm64ec-data-sym.obj
+RUN: llvm-mc -filetype=obj -triple=x86_64-windows x86_64-data-sym.s -o x86_64-data-sym.obj
+RUN: lld-link -out:test.dll -machine:arm64ec arm64ec-data-sym.obj x86_64-data-sym.obj -dll -noentry
+
+RUN: llvm-readobj --hex-dump=.data test.dll | FileCheck -check-prefix=ARM64EC-DATA %s
+ARM64EC-DATA: 0x180001000 00100080 01000000 08100080 01000000
+
+RUN: llvm-readobj --coff-basereloc test.dll | FileCheck -check-prefix=RELOCS %s
+RELOCS:      BaseReloc [
+RELOCS-NEXT:   Entry {
+RELOCS-NEXT:     Type: DIR64
+RELOCS-NEXT:     Address: 0x1000
+RELOCS-NEXT:   }
+RELOCS-NEXT:   Entry {
+RELOCS-NEXT:     Type: DIR64
+RELOCS-NEXT:     Address: 0x1008
+RELOCS-NEXT:   }
+RELOCS-NEXT: ]
+
+#--- arm64ec-data-sym.s
+        .data
+        .globl arm64ec_data_sym
+        .p2align 2, 0x0
+arm64ec_data_sym:
+        .xword arm64ec_data_sym
+
+#--- x86_64-data-sym.s
+        .data
+        .globl x86_64_data_sym
+        .p2align 2, 0x0
+x86_64_data_sym:
+        .quad x86_64_data_sym



More information about the llvm-commits mailing list