[lld] r226643 - [ELF] Minimal implementation for ARM static linking

Greg Fitzgerald garious at gmail.com
Tue Jan 20 23:35:48 PST 2015


Author: garious
Date: Wed Jan 21 01:35:48 2015
New Revision: 226643

URL: http://llvm.org/viewvc/llvm-project?rev=226643&view=rev
Log:
[ELF] Minimal implementation for ARM static linking

The code is able to statically link the simplest case of:

  int main() { return 0; }

* Only works with ARM code - no Thumb code, no interwork (-marm -mno-thumb-interwork)
* musl libc built with no interwork and no Thumb code

Differential Revision: http://reviews.llvm.org/D6716

From: Denis Protivensky <dprotivensky at accesssoftek.com>

Added:
    lld/trunk/lib/ReaderWriter/ELF/ARM/
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFFile.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFReader.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTarget.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp
    lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h
    lld/trunk/lib/ReaderWriter/ELF/ARM/CMakeLists.txt
    lld/trunk/lib/ReaderWriter/ELF/ARM/Makefile
    lld/trunk/lib/ReaderWriter/ELF/ARM/TODO.rst
    lld/trunk/test/elf/ARM/
    lld/trunk/test/elf/ARM/defsym.test
    lld/trunk/test/elf/ARM/rel-abs32.test
    lld/trunk/test/elf/ARM/rel-arm-call.test
Modified:
    lld/trunk/docs/open_projects.rst
    lld/trunk/lib/Driver/GnuLdDriver.cpp
    lld/trunk/lib/ReaderWriter/ELF/Atoms.h
    lld/trunk/lib/ReaderWriter/ELF/CMakeLists.txt
    lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp
    lld/trunk/lib/ReaderWriter/ELF/Targets.h

Modified: lld/trunk/docs/open_projects.rst
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/docs/open_projects.rst?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/docs/open_projects.rst (original)
+++ lld/trunk/docs/open_projects.rst Wed Jan 21 01:35:48 2015
@@ -8,6 +8,7 @@ Open Projects
 .. include:: ../lib/Driver/TODO.rst
 .. include:: ../lib/ReaderWriter/ELF/X86_64/TODO.rst
 .. include:: ../lib/ReaderWriter/ELF/AArch64/TODO.rst
+.. include:: ../lib/ReaderWriter/ELF/ARM/TODO.rst
 .. include:: ../tools/lld/TODO.txt
 
 Documentation TODOs

Modified: lld/trunk/lib/Driver/GnuLdDriver.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/Driver/GnuLdDriver.cpp?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/lib/Driver/GnuLdDriver.cpp (original)
+++ lld/trunk/lib/Driver/GnuLdDriver.cpp Wed Jan 21 01:35:48 2015
@@ -192,6 +192,10 @@ getArchType(const llvm::Triple &triple,
     if (value == "aarch64linux")
       return llvm::Triple::aarch64;
     return llvm::None;
+  case llvm::Triple::arm:
+    if (value == "armelf_linux_eabi")
+      return llvm::Triple::arm;
+    return llvm::None;
   default:
     return llvm::None;
   }

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFFile.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFFile.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFFile.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFFile.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,41 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMELFFile.h ----------------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_ELF_FILE_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_ELF_FILE_H
+
+#include "ELFReader.h"
+
+namespace lld {
+namespace elf {
+
+class ARMLinkingContext;
+
+template <class ELFT> class ARMELFFile : public ELFFile<ELFT> {
+public:
+  ARMELFFile(std::unique_ptr<MemoryBuffer> mb, bool atomizeStrings)
+      : ELFFile<ELFT>(std::move(mb), atomizeStrings) {}
+
+  static ErrorOr<std::unique_ptr<ARMELFFile>>
+  create(std::unique_ptr<MemoryBuffer> mb, bool atomizeStrings) {
+    return std::unique_ptr<ARMELFFile<ELFT>>(
+        new ARMELFFile<ELFT>(std::move(mb), atomizeStrings));
+  }
+};
+
+template <class ELFT> class ARMDynamicFile : public DynamicFile<ELFT> {
+public:
+  ARMDynamicFile(const ARMLinkingContext &context, StringRef name)
+      : DynamicFile<ELFT>(context, name) {}
+};
+
+} // elf
+} // lld
+
+#endif // LLD_READER_WRITER_ELF_ARM_ARM_ELF_FILE_H

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFReader.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFReader.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFReader.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMELFReader.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,60 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMELFReader.h --------------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ARM_ARM_ELF_READER_H
+#define LLD_READER_WRITER_ARM_ARM_ELF_READER_H
+
+#include "ARMELFFile.h"
+#include "ELFReader.h"
+
+namespace lld {
+namespace elf {
+
+typedef llvm::object::ELFType<llvm::support::little, 2, false> ARMELFType;
+
+struct ARMDynamicFileCreateELFTraits {
+  typedef llvm::ErrorOr<std::unique_ptr<lld::SharedLibraryFile>> result_type;
+
+  template <class ELFT>
+  static result_type create(std::unique_ptr<llvm::MemoryBuffer> mb,
+                            bool useUndefines) {
+    return lld::elf::ARMDynamicFile<ELFT>::create(std::move(mb), useUndefines);
+  }
+};
+
+struct ARMELFFileCreateELFTraits {
+  typedef llvm::ErrorOr<std::unique_ptr<lld::File>> result_type;
+
+  template <class ELFT>
+  static result_type create(std::unique_ptr<llvm::MemoryBuffer> mb,
+                            bool atomizeStrings) {
+    return lld::elf::ARMELFFile<ELFT>::create(std::move(mb), atomizeStrings);
+  }
+};
+
+class ARMELFObjectReader
+    : public ELFObjectReader<ARMELFType, ARMELFFileCreateELFTraits> {
+public:
+  ARMELFObjectReader(bool atomizeStrings)
+      : ELFObjectReader<ARMELFType, ARMELFFileCreateELFTraits>(
+            atomizeStrings, llvm::ELF::EM_ARM) {}
+};
+
+class ARMELFDSOReader
+    : public ELFDSOReader<ARMELFType, ARMDynamicFileCreateELFTraits> {
+public:
+  ARMELFDSOReader(bool useUndefines)
+      : ELFDSOReader<ARMELFType, ARMDynamicFileCreateELFTraits>(
+            useUndefines, llvm::ELF::EM_ARM) {}
+};
+
+} // namespace elf
+} // namespace lld
+
+#endif // LLD_READER_WRITER_ARM_ARM_ELF_READER_H

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,58 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMExecutableWriter.h -------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_EXECUTABLE_WRITER_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_EXECUTABLE_WRITER_H
+
+#include "ExecutableWriter.h"
+#include "ARMLinkingContext.h"
+
+namespace lld {
+namespace elf {
+
+template <class ELFT>
+class ARMExecutableWriter : public ExecutableWriter<ELFT> {
+public:
+  ARMExecutableWriter(ARMLinkingContext &context,
+                      ARMTargetLayout<ELFT> &layout);
+
+protected:
+  // Add any runtime files and their atoms to the output
+  bool createImplicitFiles(std::vector<std::unique_ptr<File>> &) override;
+
+  void finalizeDefaultAtomValues() override {
+    // Finalize the atom values that are part of the parent.
+    ExecutableWriter<ELFT>::finalizeDefaultAtomValues();
+  }
+
+  void addDefaultAtoms() override {
+    ExecutableWriter<ELFT>::addDefaultAtoms();
+  }
+
+private:
+  ARMLinkingContext &_context;
+  ARMTargetLayout<ELFT> &_armLayout;
+};
+
+template <class ELFT>
+ARMExecutableWriter<ELFT>::ARMExecutableWriter(ARMLinkingContext &context,
+                                               ARMTargetLayout<ELFT> &layout)
+    : ExecutableWriter<ELFT>(context, layout), _context(context),
+      _armLayout(layout) {}
+
+template <class ELFT>
+bool ARMExecutableWriter<ELFT>::createImplicitFiles(
+    std::vector<std::unique_ptr<File>> &result) {
+  ExecutableWriter<ELFT>::createImplicitFiles(result);
+  return true;
+}
+
+} // namespace elf
+} // namespace lld
+
+#endif // LLD_READER_WRITER_ELF_ARM_ARM_EXECUTABLE_WRITER_H

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp Wed Jan 21 01:35:48 2015
@@ -0,0 +1,21 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMLinkingContext.cpp -------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "ARMLinkingContext.h"
+#include "ARMRelocationPass.h"
+
+using namespace lld;
+using namespace lld::elf;
+
+void elf::ARMLinkingContext::addPasses(PassManager &pm) {
+  auto pass = createARMRelocationPass(*this);
+  if (pass)
+    pm.add(std::move(pass));
+  ELFLinkingContext::addPasses(pm);
+}

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,40 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMLinkingContext.h ---------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_LINKING_CONTEXT_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_LINKING_CONTEXT_H
+
+#include "ARMTargetHandler.h"
+
+#include "lld/ReaderWriter/ELFLinkingContext.h"
+
+#include "llvm/Object/ELF.h"
+#include "llvm/Support/ELF.h"
+
+namespace lld {
+namespace elf {
+
+class ARMLinkingContext final : public ELFLinkingContext {
+public:
+  ARMLinkingContext(llvm::Triple triple)
+      : ELFLinkingContext(triple, std::unique_ptr<TargetHandlerBase>(
+                                      new ARMTargetHandler(*this))) {}
+
+  void addPasses(PassManager &) override;
+
+  uint64_t getBaseAddress() const override {
+    if (_baseAddress == 0)
+      return 0x400000;
+    return _baseAddress;
+  }
+};
+} // end namespace elf
+} // end namespace lld
+
+#endif

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp Wed Jan 21 01:35:48 2015
@@ -0,0 +1,109 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.cpp ----------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "ARMTargetHandler.h"
+#include "ARMLinkingContext.h"
+
+#include "llvm/Support/Debug.h"
+#include "llvm/Support/MathExtras.h"
+
+using namespace lld;
+using namespace elf;
+
+static Reference::Addend readAddend_ARM_CALL(const uint8_t *location) {
+  const auto value = int32_t(
+      *reinterpret_cast<const llvm::support::little32_t *>(location));
+
+  const bool isBLX = (value & 0xF0000000) == 0xF0000000;
+  const int32_t bitH = isBLX ? ((value & 0x1000000) >> 24) : 0;
+
+  const int32_t result = ((value & 0xFFFFFF) << 2) | (bitH << 1);
+  return llvm::SignExtend64<26>(result);
+}
+
+static Reference::Addend readAddend(const uint8_t *location,
+                                    Reference::KindValue kindValue) {
+  switch (kindValue) {
+  case R_ARM_ABS32:
+    return int32_t(
+        *reinterpret_cast<const llvm::support::little32_t *>(location));
+  case R_ARM_CALL:
+    return readAddend_ARM_CALL(location);
+  default:
+    return 0;
+  }
+}
+
+static inline void applyArmReloc(uint8_t *location, uint32_t result,
+                                 uint32_t mask = 0xFFFFFFFF) {
+  assert(!(result & ~mask));
+  *reinterpret_cast<llvm::support::ulittle32_t *>(location) =
+      (uint32_t(*reinterpret_cast<llvm::support::ulittle32_t *>(location)) &
+       ~mask) | (result & mask);
+}
+
+/// \brief R_ARM_ABS32 - (S + A) | T => S + A
+static void relocR_ARM_ABS32(uint8_t *location, uint64_t P, uint64_t S,
+                             int64_t A) {
+  uint32_t result = (uint32_t)(S + A);
+  DEBUG_WITH_TYPE(
+      "ARM", llvm::dbgs() << "\t\tHandle " << LLVM_FUNCTION_NAME << " -";
+      llvm::dbgs() << " S: 0x" << Twine::utohexstr(S);
+      llvm::dbgs() << " A: 0x" << Twine::utohexstr(A);
+      llvm::dbgs() << " P: 0x" << Twine::utohexstr(P);
+      llvm::dbgs() << " result: 0x" << Twine::utohexstr(result) << "\n");
+  applyArmReloc(location, result);
+}
+
+/// \brief R_ARM_CALL - ((S + A) | T) - P => S + A - P
+static void relocR_ARM_CALL(uint8_t *location, uint64_t P, uint64_t S,
+                            int64_t A) {
+  uint32_t result = (uint32_t)((S + A) - P);
+  const uint32_t imm24 = (result & 0x03FFFFFC) >> 2;
+
+  DEBUG_WITH_TYPE(
+      "ARM", llvm::dbgs() << "\t\tHandle " << LLVM_FUNCTION_NAME << " -";
+      llvm::dbgs() << " S: 0x" << Twine::utohexstr(S);
+      llvm::dbgs() << " A: 0x" << Twine::utohexstr(A);
+      llvm::dbgs() << " P: 0x" << Twine::utohexstr(P);
+      llvm::dbgs() << " result: 0x" << Twine::utohexstr(result) << "\n");
+  applyArmReloc(location, imm24, 0xFFFFFF);
+}
+
+std::error_code ARMTargetRelocationHandler::applyRelocation(
+    ELFWriter &writer, llvm::FileOutputBuffer &buf, const lld::AtomLayout &atom,
+    const Reference &ref) const {
+  uint8_t *atomContent = buf.getBufferStart() + atom._fileOffset;
+  uint8_t *location = atomContent + ref.offsetInAtom();
+  uint64_t targetVAddress = writer.addressOfAtom(ref.target());
+  uint64_t relocVAddress = atom._virtualAddr + ref.offsetInAtom();
+
+  if (ref.kindNamespace() != Reference::KindNamespace::ELF)
+    return std::error_code();
+  assert(ref.kindArch() == Reference::KindArch::ARM);
+
+  // Calculate proper initial addend for the relocation
+  const Reference::Addend addend =
+      readAddend(location, ref.kindValue());
+
+  switch (ref.kindValue()) {
+  case R_ARM_NONE:
+    break;
+  case R_ARM_ABS32:
+    relocR_ARM_ABS32(location, relocVAddress, targetVAddress, addend);
+    break;
+  case R_ARM_CALL:
+    relocR_ARM_CALL(location, relocVAddress, targetVAddress, addend);
+    break;
+  default:
+    make_unhandled_reloc_error();
+  }
+
+  return std::error_code();
+}

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,32 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMRelocationHandler.h ------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_RELOCATION_HANDLER_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_RELOCATION_HANDLER_H
+
+#include "ARMTargetHandler.h"
+
+namespace lld {
+namespace elf {
+typedef llvm::object::ELFType<llvm::support::little, 2, false> ARMELFType;
+
+template <class ELFT> class ARMTargetLayout;
+
+class ARMTargetRelocationHandler final
+    : public TargetRelocationHandler {
+public:
+  std::error_code applyRelocation(ELFWriter &, llvm::FileOutputBuffer &,
+                                  const lld::AtomLayout &,
+                                  const Reference &) const override;
+};
+
+} // end namespace elf
+} // end namespace lld
+
+#endif // LLD_READER_WRITER_ELF_ARM_ARM_RELOCATION_HANDLER_H

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp Wed Jan 21 01:35:48 2015
@@ -0,0 +1,138 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMRelocationPass.cpp -------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+/// \brief Defines the relocation processing pass for ARM. This includes
+///   GOT and PLT entries, TLS, COPY, and ifunc.
+///
+/// This also includes additional behavior that gnu-ld and gold implement but
+/// which is not specified anywhere.
+///
+//===----------------------------------------------------------------------===//
+
+#include "ARMRelocationPass.h"
+
+#include "lld/Core/Simple.h"
+
+#include "llvm/ADT/DenseMap.h"
+
+#include "Atoms.h"
+#include "ARMLinkingContext.h"
+#include "llvm/Support/Debug.h"
+
+using namespace lld;
+using namespace lld::elf;
+using namespace llvm::ELF;
+
+namespace {
+class ELFPassFile : public SimpleFile {
+public:
+  ELFPassFile(const ELFLinkingContext &eti) : SimpleFile("ELFPassFile") {
+    setOrdinal(eti.getNextOrdinalAndIncrement());
+  }
+
+  llvm::BumpPtrAllocator _alloc;
+};
+
+/// \brief CRTP base for handling relocations.
+template <class Derived> class ARMRelocationPass : public Pass {
+  /// \brief Handle a specific reference.
+  void handleReference(const DefinedAtom &atom, const Reference &ref) {
+    DEBUG_WITH_TYPE(
+        "ARM", llvm::dbgs() << "\t" << LLVM_FUNCTION_NAME << "()"
+            << ":   Name of Defined Atom: " << atom.name().str();
+        llvm::dbgs() << "   kindValue: " << ref.kindValue() << "\n");
+    if (ref.kindNamespace() != Reference::KindNamespace::ELF)
+      return;
+    assert(ref.kindArch() == Reference::KindArch::ARM);
+    switch (ref.kindValue()) {
+    }
+  }
+
+protected:
+public:
+  ARMRelocationPass(const ELFLinkingContext &ctx)
+      : _file(ctx), _ctx(ctx) {}
+
+  /// \brief Do the pass.
+  ///
+  /// The goal here is to first process each reference individually. Each call
+  /// to handleReference may modify the reference itself and/or create new
+  /// atoms which must be stored in one of the maps below.
+  ///
+  /// After all references are handled, the atoms created during that are all
+  /// added to mf.
+  void perform(std::unique_ptr<MutableFile> &mf) override {
+    ScopedTask task(getDefaultDomain(), "ARM GOT/PLT Pass");
+    DEBUG_WITH_TYPE(
+        "ARM", llvm::dbgs() << "Undefined Atoms" << "\n";
+        for (const auto &atom
+             : mf->undefined()) {
+          llvm::dbgs() << " Name of Atom: " << atom->name().str() << "\n";
+        }
+
+        llvm::dbgs() << "Shared Library Atoms" << "\n";
+        for (const auto &atom
+             : mf->sharedLibrary()) {
+          llvm::dbgs() << " Name of Atom: " << atom->name().str() << "\n";
+        }
+
+        llvm::dbgs() << "Absolute Atoms" << "\n";
+        for (const auto &atom
+             : mf->absolute()) {
+          llvm::dbgs() << " Name of Atom: " << atom->name().str() << "\n";
+        }
+
+        llvm::dbgs() << "Defined Atoms" << "\n";
+        for (const auto &atom
+             : mf->defined()) {
+          llvm::dbgs() << " Name of Atom: " << atom->name().str() << "\n";
+        });
+
+    // Process all references.
+    for (const auto &atom : mf->defined()) {
+      for (const auto &ref : *atom) {
+        handleReference(*atom, *ref);
+      }
+    }
+  }
+
+protected:
+  /// \brief Owner of all the Atoms created by this pass.
+  ELFPassFile _file;
+  const ELFLinkingContext &_ctx;
+};
+
+/// This implements the static relocation model. Meaning GOT and PLT entries are
+/// not created for references that can be directly resolved. These are
+/// converted to a direct relocation. For entries that do require a GOT or PLT
+/// entry, that entry is statically bound.
+///
+/// TLS always assumes module 1 and attempts to remove indirection.
+class ARMStaticRelocationPass final
+    : public ARMRelocationPass<ARMStaticRelocationPass> {
+public:
+  ARMStaticRelocationPass(const elf::ARMLinkingContext &ctx)
+      : ARMRelocationPass(ctx) {}
+};
+
+} // end anon namespace
+
+std::unique_ptr<Pass>
+lld::elf::createARMRelocationPass(const ARMLinkingContext &ctx) {
+  switch (ctx.getOutputELFType()) {
+  case llvm::ELF::ET_EXEC:
+    if (ctx.isDynamic())
+      llvm_unreachable("Unhandled output file type");
+    else
+      return std::unique_ptr<Pass>(new ARMStaticRelocationPass(ctx));
+  default:
+    llvm_unreachable("Unhandled output file type");
+  }
+}

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,31 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMRelocationPass.h ---------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+/// \brief Declares the relocation processing pass for ARM. This includes
+///   GOT and PLT entries, TLS, COPY, and ifunc.
+///
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_RELOCATION_PASS_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_RELOCATION_PASS_H
+
+#include <memory>
+
+namespace lld {
+class Pass;
+namespace elf {
+class ARMLinkingContext;
+
+/// \brief Create ARM relocation pass for the given linking context.
+std::unique_ptr<Pass> createARMRelocationPass(const ARMLinkingContext &);
+}
+}
+
+#endif

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTarget.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTarget.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTarget.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTarget.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,10 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMTarget.h -----------------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "ARMLinkingContext.h"

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp Wed Jan 21 01:35:48 2015
@@ -0,0 +1,43 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMTargetHandler.cpp --------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "Atoms.h"
+#include "ARMExecutableWriter.h"
+#include "ARMTargetHandler.h"
+#include "ARMLinkingContext.h"
+
+using namespace lld;
+using namespace elf;
+
+ARMTargetHandler::ARMTargetHandler(ARMLinkingContext &context)
+    : _context(context), _armTargetLayout(
+          new ARMTargetLayout<ARMELFType>(context)),
+      _armRelocationHandler(new ARMTargetRelocationHandler()) {}
+
+void ARMTargetHandler::registerRelocationNames(Registry &registry) {
+  registry.addKindTable(Reference::KindNamespace::ELF, Reference::KindArch::ARM,
+                        kindStrings);
+}
+
+std::unique_ptr<Writer> ARMTargetHandler::getWriter() {
+  switch (this->_context.getOutputELFType()) {
+  case llvm::ELF::ET_EXEC:
+    return std::unique_ptr<Writer>(
+        new ARMExecutableWriter<ARMELFType>(_context, *_armTargetLayout.get()));
+  default:
+    llvm_unreachable("unsupported output type");
+  }
+}
+
+#define ELF_RELOC(name, value) LLD_KIND_STRING_ENTRY(name),
+
+const Registry::KindStrings ARMTargetHandler::kindStrings[] = {
+#include "llvm/Support/ELFRelocs/ARM.def"
+    LLD_KIND_STRING_END
+};

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h Wed Jan 21 01:35:48 2015
@@ -0,0 +1,68 @@
+//===--------- lib/ReaderWriter/ELF/ARM/ARMTargetHandler.h ----------------===//
+//
+//                             The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLD_READER_WRITER_ELF_ARM_ARM_TARGET_HANDLER_H
+#define LLD_READER_WRITER_ELF_ARM_ARM_TARGET_HANDLER_H
+
+#include "ARMELFFile.h"
+#include "ARMELFReader.h"
+#include "ARMRelocationHandler.h"
+#include "DefaultTargetHandler.h"
+#include "TargetLayout.h"
+
+#include "lld/Core/Simple.h"
+#include "llvm/ADT/Optional.h"
+#include <map>
+
+namespace lld {
+namespace elf {
+typedef llvm::object::ELFType<llvm::support::little, 2, false> ARMELFType;
+class ARMLinkingContext;
+
+template <class ELFT> class ARMTargetLayout : public TargetLayout<ELFT> {
+public:
+  ARMTargetLayout(ARMLinkingContext &context)
+      : TargetLayout<ELFT>(context) {}
+};
+
+class ARMTargetHandler final : public DefaultTargetHandler<ARMELFType> {
+public:
+  ARMTargetHandler(ARMLinkingContext &context);
+
+  ARMTargetLayout<ARMELFType> &getTargetLayout() override {
+    return *(_armTargetLayout.get());
+  }
+
+  void registerRelocationNames(Registry &registry) override;
+
+  const ARMTargetRelocationHandler &getRelocationHandler() const override {
+    return *(_armRelocationHandler.get());
+  }
+
+  std::unique_ptr<Reader> getObjReader(bool atomizeStrings) override {
+    return std::unique_ptr<Reader>(new ARMELFObjectReader(atomizeStrings));
+  }
+
+  std::unique_ptr<Reader> getDSOReader(bool useShlibUndefines) override {
+    return std::unique_ptr<Reader>(new ARMELFDSOReader(useShlibUndefines));
+  }
+
+  std::unique_ptr<Writer> getWriter() override;
+
+private:
+  static const Registry::KindStrings kindStrings[];
+  ARMLinkingContext &_context;
+  std::unique_ptr<ARMTargetLayout<ARMELFType>> _armTargetLayout;
+  std::unique_ptr<ARMTargetRelocationHandler> _armRelocationHandler;
+};
+
+} // end namespace elf
+} // end namespace lld
+
+#endif // LLD_READER_WRITER_ELF_ARM_ARM_TARGET_HANDLER_H

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/CMakeLists.txt?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/CMakeLists.txt (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/CMakeLists.txt Wed Jan 21 01:35:48 2015
@@ -0,0 +1,10 @@
+add_lld_library(lldARMELFTarget
+  ARMLinkingContext.cpp
+  ARMTargetHandler.cpp
+  ARMRelocationHandler.cpp
+  ARMRelocationPass.cpp
+  )
+
+target_link_libraries(lldARMELFTarget ${cmake_2_8_12_INTERFACE}
+  lldCore
+  )

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/Makefile
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/Makefile?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/Makefile (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/Makefile Wed Jan 21 01:35:48 2015
@@ -0,0 +1,15 @@
+##===------ lld/lib/ReaderWriter/ELF/ARM/Makefile ----------*- Makefile -*-===##
+#
+#                     The LLVM Compiler Infrastructure
+#
+# This file is distributed under the University of Illinois Open Source
+# License. See LICENSE.TXT for details.
+#
+##===----------------------------------------------------------------------===##
+
+LLD_LEVEL := ../../../..
+LIBRARYNAME := lldARMELFTarget
+USEDLIBS = lldCore.a
+CPP.Flags += -I$(PROJ_SRC_DIR)/$(LLD_LEVEL)/lib/ReaderWriter/ELF/ARM -I$(PROJ_SRC_DIR)/$(LLD_LEVEL)/lib/ReaderWriter/ELF
+
+include $(LLD_LEVEL)/Makefile

Added: lld/trunk/lib/ReaderWriter/ELF/ARM/TODO.rst
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ARM/TODO.rst?rev=226643&view=auto
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ARM/TODO.rst (added)
+++ lld/trunk/lib/ReaderWriter/ELF/ARM/TODO.rst Wed Jan 21 01:35:48 2015
@@ -0,0 +1,20 @@
+ELF ARM
+~~~~~~~~~~~
+
+Unimplemented Features
+######################
+
+* Static executable linking - in progress
+* Dynamic executable linking
+* DSO linking
+* PLT entries' generation for images larger than 2^28 bytes (see Sec. A.3 of the ELF reference)
+* ARM and Thumb interworking (see http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0203j/Bcghfebi.html)
+* .ARM.exidx section handling
+* -init/-fini options
+* Lots of relocations
+
+Unimplemented Relocations
+#########################
+
+All of these relocations are defined in:
+http://infocenter.arm.com/help/topic/com.arm.doc.ihi0044e/IHI0044E_aaelf.pdf

Modified: lld/trunk/lib/ReaderWriter/ELF/Atoms.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/Atoms.h?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/Atoms.h (original)
+++ lld/trunk/lib/ReaderWriter/ELF/Atoms.h Wed Jan 21 01:35:48 2015
@@ -682,6 +682,11 @@ public:
                                Reference::Addend a) {
     this->addReferenceELF(Reference::KindArch::AArch64, relocType, off, t, a);
   }
+
+  void addReferenceELF_ARM(uint16_t relocType, uint64_t off, const Atom *t,
+                               Reference::Addend a) {
+    this->addReferenceELF(Reference::KindArch::ARM, relocType, off, t, a);
+  }
 };
 
 /// \brief Atom which represents an object for which a COPY relocation will be

Modified: lld/trunk/lib/ReaderWriter/ELF/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/CMakeLists.txt?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/CMakeLists.txt (original)
+++ lld/trunk/lib/ReaderWriter/ELF/CMakeLists.txt Wed Jan 21 01:35:48 2015
@@ -14,6 +14,7 @@ target_link_libraries(lldELF ${cmake_2_8
   lldX86ELFTarget
   lldX86_64ELFTarget
   lldAArch64ELFTarget
+  lldARMELFTarget
   )
 
 include_directories(.)
@@ -24,3 +25,4 @@ add_subdirectory(PPC)
 add_subdirectory(Mips)
 add_subdirectory(Hexagon)
 add_subdirectory(AArch64)
+add_subdirectory(ARM)

Modified: lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp (original)
+++ lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp Wed Jan 21 01:35:48 2015
@@ -85,6 +85,8 @@ uint16_t ELFLinkingContext::getOutputMac
     return llvm::ELF::EM_PPC;
   case llvm::Triple::aarch64:
     return llvm::ELF::EM_AARCH64;
+  case llvm::Triple::arm:
+    return llvm::ELF::EM_ARM;
   default:
     llvm_unreachable("Unhandled arch");
   }
@@ -148,6 +150,9 @@ ELFLinkingContext::create(llvm::Triple t
   case llvm::Triple::aarch64:
     return std::unique_ptr<ELFLinkingContext>(
         new lld::elf::AArch64LinkingContext(triple));
+  case llvm::Triple::arm:
+    return std::unique_ptr<ELFLinkingContext>(
+        new lld::elf::ARMLinkingContext(triple));
   default:
     return nullptr;
   }

Modified: lld/trunk/lib/ReaderWriter/ELF/Targets.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/Targets.h?rev=226643&r1=226642&r2=226643&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/Targets.h (original)
+++ lld/trunk/lib/ReaderWriter/ELF/Targets.h Wed Jan 21 01:35:48 2015
@@ -11,6 +11,7 @@
 #define LLD_READER_WRITER_ELF_TARGETS_H
 
 #include "AArch64/AArch64Target.h"
+#include "ARM/ARMTarget.h"
 #include "Hexagon/HexagonTarget.h"
 #include "Mips/MipsTarget.h"
 #include "PPC/PPCTarget.h"

Added: lld/trunk/test/elf/ARM/defsym.test
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf/ARM/defsym.test?rev=226643&view=auto
==============================================================================
--- lld/trunk/test/elf/ARM/defsym.test (added)
+++ lld/trunk/test/elf/ARM/defsym.test Wed Jan 21 01:35:48 2015
@@ -0,0 +1,74 @@
+# Check that defined symbols are present in the generated executable
+
+# RUN: yaml2obj -format=elf %s > %t-o.o
+# RUN: lld -flavor gnu -target arm-linux-gnu --defsym=main=fn -e=fn \
+# RUN: -static --noinhibit-exec %t-o.o -o %t
+# RUN: llvm-readobj -symbols %t | FileCheck %s
+
+# CHECK: Symbol {
+# CHECK:   Name: main (1)
+# CHECK:   Value: 0x400075
+# CHECK:   Size: 0
+# CHECK:   Binding: Global (0x1)
+# CHECK:   Type: Function (0x2)
+# CHECK:   Other: 0
+# CHECK:   Section: .text (0x1)
+# CHECK: }
+# CHECK: Symbol {
+# CHECK:   Name: fn (6)
+# CHECK:   Value: 0x400075
+# CHECK:   Size: 15
+# CHECK:   Binding: Global (0x1)
+# CHECK:   Type: Function (0x2)
+# CHECK:   Other: 0
+# CHECK:   Section: .text (0x1)
+# CHECK: }
+
+---
+FileHeader:
+  Class:           ELFCLASS32
+  Data:            ELFDATA2LSB
+  Type:            ET_REL
+  Machine:         EM_ARM
+  Flags:           [ EF_ARM_EABI_VER5 ]
+Sections:
+  - Name:            .text
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_ALLOC, SHF_EXECINSTR ]
+    AddressAlign:    0x0000000000000004
+    Content:         80B400AF00231846BD465DF8047B7047
+  - Name:            .data
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+  - Name:            .bss
+    Type:            SHT_NOBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+  - Name:            .note.GNU-stack
+    Type:            SHT_PROGBITS
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+Symbols:
+  Local:
+    - Name:            .text
+      Type:            STT_SECTION
+      Section:         .text
+    - Name:            .data
+      Type:            STT_SECTION
+      Section:         .data
+    - Name:            .bss
+      Type:            STT_SECTION
+      Section:         .bss
+    - Name:            .note.GNU-stack
+      Type:            STT_SECTION
+      Section:         .note.GNU-stack
+  Global:
+    - Name:            fn
+      Type:            STT_FUNC
+      Section:         .text
+      Value:           0x0000000000000001
+      Size:            0x0000000000000010
+...

Added: lld/trunk/test/elf/ARM/rel-abs32.test
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf/ARM/rel-abs32.test?rev=226643&view=auto
==============================================================================
--- lld/trunk/test/elf/ARM/rel-abs32.test (added)
+++ lld/trunk/test/elf/ARM/rel-abs32.test Wed Jan 21 01:35:48 2015
@@ -0,0 +1,59 @@
+# Check handling of R_ARM_ABS32 relocation.
+# RUN: yaml2obj -format=elf %s > %t-o.o
+# RUN: lld -flavor gnu -target arm -m armelf_linux_eabi -Bstatic \
+# RUN: --noinhibit-exec %t-o.o -o %t
+# RUN: llvm-objdump -s -t %t | FileCheck %s
+
+# CHECK: Contents of section .data:
+# CHECK-NEXT: 401000 84004000
+#      data = 0x400084 ^^
+#               data     main addr  content
+#             0x400084 = 0x400074 + 0x10
+# CHECK: SYMBOL TABLE:
+# CHECK: 00400074 g     F .text  0000001c main
+# CHECK: 00401000 g       .data  00000004 data
+
+---
+FileHeader:
+  Class:           ELFCLASS32
+  Data:            ELFDATA2LSB
+  Type:            ET_REL
+  Machine:         EM_ARM
+  Flags:           [ EF_ARM_EABI_VER5 ]
+Sections:
+  - Name:            .text
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_ALLOC, SHF_EXECINSTR ]
+    AddressAlign:    0x0000000000000004
+    Content:         04B02DE500B08DE20030A0E30300A0E100D04BE204B09DE41EFF2FE1
+  - Name:            .data
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000004
+    Content:         '10000000'
+  - Name:            .rel.data
+    Type:            SHT_REL
+    Link:            .symtab
+    AddressAlign:    0x0000000000000004
+    Info:            .data
+    Relocations:
+      - Offset:          0x0000000000000000
+        Symbol:          main
+        Type:            R_ARM_ABS32
+        Addend:          0
+  - Name:            .bss
+    Type:            SHT_NOBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+Symbols:
+  Global:
+    - Name:            main
+      Type:            STT_FUNC
+      Section:         .text
+      Size:            0x000000000000001C
+    - Name:            data
+      Type:            STT_OBJECT
+      Section:         .data
+      Size:            0x0000000000000004
+...

Added: lld/trunk/test/elf/ARM/rel-arm-call.test
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf/ARM/rel-arm-call.test?rev=226643&view=auto
==============================================================================
--- lld/trunk/test/elf/ARM/rel-arm-call.test (added)
+++ lld/trunk/test/elf/ARM/rel-arm-call.test Wed Jan 21 01:35:48 2015
@@ -0,0 +1,60 @@
+# Check handling of R_ARM_CALL relocation.
+# RUN: yaml2obj -format=elf %s > %t-o.o
+# RUN: lld -flavor gnu -target arm -m armelf_linux_eabi -Bstatic \
+# RUN: --noinhibit-exec %t-o.o -o %t
+# RUN: llvm-objdump -s -t %t | FileCheck %s
+
+# CHECK: Contents of section .text:
+# CHECK: 400084 1eff2fe1 00482de9 04b08de2 f7ffffeb
+#                          offset = -0x24  ^^
+#               call site  offset  PC(arm) _Z1fv addr
+#               0x400090 + (-0x24) + 0x8 = 0x400074
+# CHECK: SYMBOL TABLE:
+# CHECK: 00400074 g     F .text  00000014 _Z1fv
+# CHECK: 00400088 g     F .text  00000018 main
+
+---
+FileHeader:
+  Class:           ELFCLASS32
+  Data:            ELFDATA2LSB
+  Type:            ET_REL
+  Machine:         EM_ARM
+  Flags:           [ EF_ARM_EABI_VER5 ]
+Sections:
+  - Name:            .text
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_ALLOC, SHF_EXECINSTR ]
+    AddressAlign:    0x0000000000000004
+    Content:         04B02DE500B08DE200D04BE204B09DE41EFF2FE100482DE904B08DE2FEFFFFEB0030A0E30300A0E10088BDE8
+  - Name:            .rel.text
+    Type:            SHT_REL
+    Link:            .symtab
+    AddressAlign:    0x0000000000000004
+    Info:            .text
+    Relocations:
+      - Offset:          0x000000000000001C
+        Symbol:          _Z1fv
+        Type:            R_ARM_CALL
+        Addend:          0
+  - Name:            .data
+    Type:            SHT_PROGBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+  - Name:            .bss
+    Type:            SHT_NOBITS
+    Flags:           [ SHF_WRITE, SHF_ALLOC ]
+    AddressAlign:    0x0000000000000001
+    Content:         ''
+Symbols:
+  Global:
+    - Name:            _Z1fv
+      Type:            STT_FUNC
+      Section:         .text
+      Size:            0x0000000000000014
+    - Name:            main
+      Type:            STT_FUNC
+      Section:         .text
+      Value:           0x0000000000000014
+      Size:            0x0000000000000018
+...





More information about the llvm-commits mailing list