Files
clang-p2996/lld/lib/ReaderWriter/PECOFF/LinkerGeneratedSymbolFile.h
Shankar Easwaran d26c8e3463 [lld][LinkingContext] Atoms created from command line options should be available in YAML
This adds an API to the LinkingContext for flavors to add Internal files
containing atoms that need to appear in the YAML output as well, when -emit-yaml
switch is used.

Flavors can add more internal files for other options that are needed.

llvm-svn: 189718
2013-08-31 05:27:38 +00:00

116 lines
3.7 KiB
C++

//===- lib/ReaderWriter/PECOFF/LinkerGeneratedSymbolFile.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 "GroupedSectionsPass.h"
#include "IdataPass.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/Support/Allocator.h"
#include "llvm/Support/Path.h"
#include "lld/Core/ArchiveLibraryFile.h"
#include "lld/Core/InputFiles.h"
#include "lld/Core/PassManager.h"
#include "lld/Passes/LayoutPass.h"
#include "lld/ReaderWriter/PECOFFLinkingContext.h"
#include "lld/ReaderWriter/Reader.h"
#include "lld/ReaderWriter/Simple.h"
#include "lld/ReaderWriter/Writer.h"
namespace lld {
namespace coff {
namespace {
// The symbol __ImageBase is a linker generated symbol. No standard library
// files define it, but the linker is expected to prepare it as if it was read
// from a file. The content of the atom is a 4-byte integer equal to the image
// base address.
//
// Note that because the name is prefixed by an underscore on x86 Win32, the
// actual symbol name becomes ___ImageBase (with three underscores). On other
// architectures names are not mangled with an underscore. We need to handle
// name mangling correctly when porting LLD Windows code to them.
class ImageBaseAtom : public COFFLinkerInternalAtom {
public:
ImageBaseAtom(const File &file, uint32_t imageBase)
: COFFLinkerInternalAtom(file, assembleRawContent(imageBase)) {}
virtual StringRef name() const { return "___ImageBase"; }
virtual uint64_t ordinal() const { return 0; }
virtual ContentType contentType() const { return typeData; }
virtual ContentPermissions permissions() const { return permRW_; }
virtual DeadStripKind deadStrip() const { return deadStripAlways; }
private:
std::vector<uint8_t> assembleRawContent(uint32_t imageBase) {
std::vector<uint8_t> data = std::vector<uint8_t>(4);
*(reinterpret_cast<uint32_t *>(&data[0])) = imageBase;
return data;
}
};
// The file to wrap ImageBaseAtom. This is the only member file of
// LinkerGeneratedSymbolFile.
class MemberFile : public SimpleFile {
public:
MemberFile(const PECOFFLinkingContext &context)
: SimpleFile(context, "Member of the Linker Internal File"),
_atom(*this, context.getBaseAddress()) {
addAtom(_atom);
};
private:
ImageBaseAtom _atom;
};
} // anonymous namespace
// A pseudo library file to wrap MemberFile, which in turn wraps ImageBaseAtom.
// The file the core linker handle is this.
//
// The reason why we don't pass MemberFile to the core linker is because, if we
// did so, ImageBaseAtom would always be emit to the resultant executable. By
// wrapping the file by a library file, we made it to emit ImageBaseAtom only
// when the atom is really referenced.
class LinkerGeneratedSymbolFile : public ArchiveLibraryFile {
public:
LinkerGeneratedSymbolFile(const PECOFFLinkingContext &context)
: ArchiveLibraryFile(context, "Linker Internal File"),
_memberFile(context) {};
virtual const File *find(StringRef name, bool dataSymbolOnly) const {
if (name == "___ImageBase")
return &_memberFile;
return nullptr;
}
virtual const atom_collection<DefinedAtom> &defined() const {
return _noDefinedAtoms;
}
virtual const atom_collection<UndefinedAtom> &undefined() const {
return _noUndefinedAtoms;
}
virtual const atom_collection<SharedLibraryAtom> &sharedLibrary() const {
return _noSharedLibraryAtoms;
}
virtual const atom_collection<AbsoluteAtom> &absolute() const {
return _noAbsoluteAtoms;
}
private:
MemberFile _memberFile;
};
} // end namespace coff
} // end namespace lld