Saleem Abdulrasool f9b99a1e07 PE/COFF: teach ARMNT backend about ADDR32NB for exports
This adds the ability to export symbols from a DLL built for ARMNT.  Add this
support first to help work towards adding support for import thunks on Windows
on ARM.  In order to generate the exports, add support for
IMAGE_REL_ARM_ADDR32NB relocations.

llvm-svn: 225339
2015-01-07 04:20:26 +00:00

95 lines
3.2 KiB
C++

//===- lib/ReaderWriter/PECOFF/Pass.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 "Pass.h"
#include "lld/Core/File.h"
#include "llvm/Support/COFF.h"
namespace lld {
namespace pecoff {
static void addReloc(COFFBaseDefinedAtom *atom, const Atom *target,
size_t offsetInAtom, Reference::KindArch arch,
Reference::KindValue relType) {
atom->addReference(llvm::make_unique<COFFReference>(
target, offsetInAtom, relType, arch));
}
void addDir64Reloc(COFFBaseDefinedAtom *atom, const Atom *target,
llvm::COFF::MachineTypes machine, size_t offsetInAtom) {
switch (machine) {
case llvm::COFF::IMAGE_FILE_MACHINE_I386:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86,
llvm::COFF::IMAGE_REL_I386_DIR32);
return;
case llvm::COFF::IMAGE_FILE_MACHINE_AMD64:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86_64,
llvm::COFF::IMAGE_REL_AMD64_ADDR64);
return;
default:
llvm_unreachable("unsupported machine type");
}
}
void addDir32Reloc(COFFBaseDefinedAtom *atom, const Atom *target,
llvm::COFF::MachineTypes machine, size_t offsetInAtom) {
switch (machine) {
case llvm::COFF::IMAGE_FILE_MACHINE_I386:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86,
llvm::COFF::IMAGE_REL_I386_DIR32);
return;
case llvm::COFF::IMAGE_FILE_MACHINE_AMD64:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86_64,
llvm::COFF::IMAGE_REL_AMD64_ADDR32);
return;
default:
llvm_unreachable("unsupported machine type");
}
}
void addDir32NBReloc(COFFBaseDefinedAtom *atom, const Atom *target,
llvm::COFF::MachineTypes machine, size_t offsetInAtom) {
switch (machine) {
case llvm::COFF::IMAGE_FILE_MACHINE_I386:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86,
llvm::COFF::IMAGE_REL_I386_DIR32NB);
return;
case llvm::COFF::IMAGE_FILE_MACHINE_AMD64:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86_64,
llvm::COFF::IMAGE_REL_AMD64_ADDR32NB);
return;
case llvm::COFF::IMAGE_FILE_MACHINE_ARMNT:
addReloc(atom, target, offsetInAtom, Reference::KindArch::ARM,
llvm::COFF::IMAGE_REL_ARM_ADDR32NB);
return;
default:
llvm_unreachable("unsupported machine type");
}
}
void addRel32Reloc(COFFBaseDefinedAtom *atom, const Atom *target,
llvm::COFF::MachineTypes machine, size_t offsetInAtom) {
switch (machine) {
case llvm::COFF::IMAGE_FILE_MACHINE_I386:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86,
llvm::COFF::IMAGE_REL_I386_REL32);
return;
case llvm::COFF::IMAGE_FILE_MACHINE_AMD64:
addReloc(atom, target, offsetInAtom, Reference::KindArch::x86_64,
llvm::COFF::IMAGE_REL_AMD64_REL32);
return;
default:
llvm_unreachable("unsupported machine type");
}
}
} // end namespace pecoff
} // end namespace lld