summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJoey Gouly <joey.gouly@gmail.com>2014-01-03 23:12:02 +0000
committerJoey Gouly <joey.gouly@gmail.com>2014-01-03 23:12:02 +0000
commitceb16dedefc7833b3f3b7305e751ad9ba748d99b (patch)
tree7158a67f016d6a8bece0f3cf0b35fd8d62f6ce46
parent0724bf67672c754aa61ce2659939450ff22c30fa (diff)
downloadbcm5719-llvm-ceb16dedefc7833b3f3b7305e751ad9ba748d99b.tar.gz
bcm5719-llvm-ceb16dedefc7833b3f3b7305e751ad9ba748d99b.zip
[MachO] Begin to add some MachO specific File/Atoms, and add the start of
normalizedToAtoms. llvm-svn: 198459
-rw-r--r--lld/lib/ReaderWriter/MachO/Atoms.h41
-rw-r--r--lld/lib/ReaderWriter/MachO/CMakeLists.txt3
-rw-r--r--lld/lib/ReaderWriter/MachO/File.h37
-rw-r--r--lld/lib/ReaderWriter/MachO/MachONormalizedFile.h6
-rw-r--r--lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp2
-rw-r--r--lld/lib/ReaderWriter/MachO/MachONormalizedFileToAtoms.cpp66
-rw-r--r--lld/lib/ReaderWriter/MachO/MachONormalizedFileYAML.cpp24
-rw-r--r--lld/unittests/MachOTests/CMakeLists.txt1
-rw-r--r--lld/unittests/MachOTests/MachONormalizedFileToAtomsTests.cpp61
9 files changed, 234 insertions, 7 deletions
diff --git a/lld/lib/ReaderWriter/MachO/Atoms.h b/lld/lib/ReaderWriter/MachO/Atoms.h
new file mode 100644
index 00000000000..7733b2a9546
--- /dev/null
+++ b/lld/lib/ReaderWriter/MachO/Atoms.h
@@ -0,0 +1,41 @@
+//===- lib/ReaderWriter/MachO/Atoms.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_MACHO_ATOMS_H
+#define LLD_READER_WRITER_MACHO_ATOMS_H
+
+#include "lld/ReaderWriter/Simple.h"
+
+namespace lld {
+namespace mach_o {
+class MachODefinedAtom : public SimpleDefinedAtom {
+public:
+ // FIXME: This constructor should also take the ContentType.
+ MachODefinedAtom(const File &f, const StringRef name,
+ const ArrayRef<uint8_t> content)
+ : SimpleDefinedAtom(f), _name(name), _content(content) {}
+
+ virtual uint64_t size() const { return rawContent().size(); }
+
+ virtual ContentType contentType() const { return DefinedAtom::typeCode; }
+
+ virtual StringRef name() const { return _name; }
+
+ virtual Scope scope() const { return scopeGlobal; }
+
+ virtual ArrayRef<uint8_t> rawContent() const { return _content; }
+
+private:
+ const StringRef _name;
+ const ArrayRef<uint8_t> _content;
+};
+} // mach_o
+} // lld
+
+#endif
diff --git a/lld/lib/ReaderWriter/MachO/CMakeLists.txt b/lld/lib/ReaderWriter/MachO/CMakeLists.txt
index d63b4d454d7..0b9b13545e0 100644
--- a/lld/lib/ReaderWriter/MachO/CMakeLists.txt
+++ b/lld/lib/ReaderWriter/MachO/CMakeLists.txt
@@ -3,6 +3,7 @@ add_lld_library(lldMachO
MachONormalizedFileBinaryReader.cpp
MachONormalizedFileBinaryWriter.cpp
MachONormalizedFileFromAtoms.cpp
+ MachONormalizedFileToAtoms.cpp
MachONormalizedFileYAML.cpp
ReferenceKinds.cpp
WriterMachO.cpp
@@ -12,3 +13,5 @@ target_link_libraries(lldMachO
lldReaderWriter
lldPasses
)
+
+include_directories(.)
diff --git a/lld/lib/ReaderWriter/MachO/File.h b/lld/lib/ReaderWriter/MachO/File.h
new file mode 100644
index 00000000000..e002a93e4b4
--- /dev/null
+++ b/lld/lib/ReaderWriter/MachO/File.h
@@ -0,0 +1,37 @@
+//===- lib/ReaderWriter/MachO/File.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_MACHO_FILE_H
+#define LLD_READER_WRITER_MACHO_FILE_H
+
+#include "Atoms.h"
+
+#include "lld/ReaderWriter/Simple.h"
+
+namespace lld {
+namespace mach_o {
+
+class MachOFile : public SimpleFile {
+public:
+ MachOFile(StringRef path) : SimpleFile(path) {}
+
+ void addDefinedAtom(StringRef name, ArrayRef<uint8_t> content) {
+ MachODefinedAtom *atom =
+ new (_allocator) MachODefinedAtom(*this, name, content);
+ addAtom(*atom);
+ }
+
+private:
+ llvm::BumpPtrAllocator _allocator;
+};
+
+} // end namespace mach_o
+} // end namespace lld
+
+#endif
diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFile.h b/lld/lib/ReaderWriter/MachO/MachONormalizedFile.h
index f2f6cf86184..15fd4c3686d 100644
--- a/lld/lib/ReaderWriter/MachO/MachONormalizedFile.h
+++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFile.h
@@ -113,7 +113,7 @@ struct Section {
SectionAttr attributes;
uint32_t alignment;
Hex64 address;
- ContentBytes content;
+ std::vector<uint8_t> content;
Relocations relocations;
IndirectSymbols indirectSymbols;
};
@@ -273,7 +273,3 @@ normalizedFromAtoms(const lld::File &atomFile, const MachOLinkingContext &ctxt);
} // namespace lld
#endif // LLD_READER_WRITER_MACHO_NORMALIZE_FILE_H
-
-
-
-
diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp b/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp
index 0d73ec81180..1479ac20da2 100644
--- a/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp
+++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp
@@ -423,7 +423,7 @@ void Util::appendSection(SectionInfo *si, NormalizedFile &file) {
// Copy content from atoms to content buffer for section.
// FIXME: zerofill atoms/sections should not take up content space.
normSect->content.resize(si->size);
- Hex8 *sectionContent = normSect->content.data();
+ uint8_t *sectionContent = normSect->content.data();
for (AtomInfo &ai : si->atomsAndOffsets) {
// Copy raw bytes.
uint8_t *atomContent = reinterpret_cast<uint8_t*>
diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFileToAtoms.cpp b/lld/lib/ReaderWriter/MachO/MachONormalizedFileToAtoms.cpp
new file mode 100644
index 00000000000..2032e0cea05
--- /dev/null
+++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFileToAtoms.cpp
@@ -0,0 +1,66 @@
+//===- lib/ReaderWriter/MachO/MachONormalizedFileToAtoms.cpp --------------===//
+//
+// The LLVM Linker
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+///
+/// \file Converts from in-memory normalized mach-o to in-memory Atoms.
+///
+/// +------------+
+/// | normalized |
+/// +------------+
+/// |
+/// |
+/// v
+/// +-------+
+/// | Atoms |
+/// +-------+
+
+#include "MachONormalizedFile.h"
+#include "File.h"
+#include "Atoms.h"
+
+#include "lld/Core/LLVM.h"
+
+#include "llvm/Support/MachO.h"
+
+using namespace llvm::MachO;
+
+namespace lld {
+namespace mach_o {
+namespace normalized {
+
+static ErrorOr<std::unique_ptr<lld::File>>
+normalizedObjectToAtoms(const NormalizedFile &normalizedFile, StringRef path) {
+ std::unique_ptr<MachOFile> file(new MachOFile(path));
+
+ for (auto &sym : normalizedFile.globalSymbols) {
+ file->addDefinedAtom(sym.name,
+ normalizedFile.sections[sym.sect - 1].content);
+ }
+
+ assert(normalizedFile.localSymbols.empty() &&
+ "local symbols not supported yet!");
+ assert(normalizedFile.undefinedSymbols.empty() &&
+ "undefined symbols not supported yet!");
+
+ return std::unique_ptr<File>(std::move(file));
+}
+
+ErrorOr<std::unique_ptr<lld::File>>
+normalizedToAtoms(const NormalizedFile &normalizedFile, StringRef path) {
+ switch (normalizedFile.fileType) {
+ case MH_OBJECT:
+ return normalizedObjectToAtoms(normalizedFile, path);
+ default:
+ llvm_unreachable("unhandled MachO file type!");
+ }
+}
+
+} // namespace normalized
+} // namespace mach_o
+} // namespace lld
diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFileYAML.cpp b/lld/lib/ReaderWriter/MachO/MachONormalizedFileYAML.cpp
index 2a888d5d3eb..78efae6adb8 100644
--- a/lld/lib/ReaderWriter/MachO/MachONormalizedFileYAML.cpp
+++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFileYAML.cpp
@@ -269,6 +269,7 @@ struct ScalarBitSetTraits<SymbolDesc> {
template <>
struct MappingTraits<Section> {
+ struct NormalizedContentBytes;
static void mapping(IO &io, Section &sect) {
io.mapRequired("segment", sect.segmentName);
io.mapRequired("section", sect.sectionName);
@@ -276,10 +277,31 @@ struct MappingTraits<Section> {
io.mapOptional("attributes", sect.attributes);
io.mapOptional("alignment", sect.alignment, 0U);
io.mapRequired("address", sect.address);
- io.mapOptional("content", sect.content);
+ MappingNormalization<NormalizedContent, std::vector<uint8_t>> content(
+ io, sect.content);
+ io.mapOptional("content", content->normalizedContent);
io.mapOptional("relocations", sect.relocations);
io.mapOptional("indirect-syms", sect.indirectSymbols);
}
+
+ // FIXME: It would be good if we could remove this, so we don't need to copy
+ // the content data.
+ struct NormalizedContent {
+ NormalizedContent(IO &) {}
+ NormalizedContent(IO &, std::vector<uint8_t> content) {
+ for (auto &c : content) {
+ normalizedContent.push_back(c);
+ }
+ }
+ std::vector<uint8_t> denormalize(IO &) {
+ std::vector<uint8_t> content;
+ for (auto &c : normalizedContent) {
+ content.push_back(c);
+ }
+ return content;
+ }
+ ContentBytes normalizedContent;
+ };
};
diff --git a/lld/unittests/MachOTests/CMakeLists.txt b/lld/unittests/MachOTests/CMakeLists.txt
index e95d261ff7c..23052d366c6 100644
--- a/lld/unittests/MachOTests/CMakeLists.txt
+++ b/lld/unittests/MachOTests/CMakeLists.txt
@@ -2,6 +2,7 @@
add_lld_unittest(lldMachOTests
MachONormalizedFileBinaryReaderTests.cpp
MachONormalizedFileBinaryWriterTests.cpp
+ MachONormalizedFileToAtomsTests.cpp
MachONormalizedFileYAMLTests.cpp
)
diff --git a/lld/unittests/MachOTests/MachONormalizedFileToAtomsTests.cpp b/lld/unittests/MachOTests/MachONormalizedFileToAtomsTests.cpp
new file mode 100644
index 00000000000..9b2859a5961
--- /dev/null
+++ b/lld/unittests/MachOTests/MachONormalizedFileToAtomsTests.cpp
@@ -0,0 +1,61 @@
+//===- lld/unittest/MachOTests/MachONormalizedFileToAtomsTests.cpp --------===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "gtest/gtest.h"
+
+#include <llvm/Support/MachO.h>
+#include "../../lib/ReaderWriter/MachO/MachONormalizedFile.h"
+
+#include <assert.h>
+#include <vector>
+
+using llvm::ErrorOr;
+
+using namespace lld::mach_o::normalized;
+using namespace llvm::MachO;
+
+unsigned countDefinedAtoms(const lld::File &file) {
+ unsigned count = 0;
+ for (const auto &d : file.defined()) {
+ (void)d;
+ ++count;
+ }
+ return count;
+}
+
+TEST(ToAtomsTest, empty_obj_x86_64) {
+ NormalizedFile f;
+ f.arch = lld::MachOLinkingContext::arch_x86_64;
+ ErrorOr<std::unique_ptr<const lld::File>> atom_f = normalizedToAtoms(f, "");
+ EXPECT_FALSE(!atom_f);
+ EXPECT_EQ(0U, countDefinedAtoms(**atom_f));
+}
+
+TEST(ToAtomsTest, basic_obj_x86_64) {
+ NormalizedFile f;
+ f.arch = lld::MachOLinkingContext::arch_x86_64;
+ Section textSection;
+ static const uint8_t contentBytes[] = { 0x55, 0x48, 0x89, 0xE5,
+ 0x31, 0xC0, 0x5D, 0xC3 };
+ const unsigned contentSize = sizeof(contentBytes) / sizeof(contentBytes[0]);
+ textSection.content.insert(textSection.content.begin(), contentBytes,
+ &contentBytes[contentSize]);
+ f.sections.push_back(textSection);
+ Symbol mainSymbol;
+ mainSymbol.name = "_main";
+ mainSymbol.type = N_SECT;
+ mainSymbol.sect = 1;
+ f.globalSymbols.push_back(mainSymbol);
+ ErrorOr<std::unique_ptr<const lld::File>> atom_f = normalizedToAtoms(f, "");
+ EXPECT_FALSE(!atom_f);
+ EXPECT_EQ(1U, countDefinedAtoms(**atom_f));
+ const lld::DefinedAtom *singleAtom = *(*atom_f)->defined().begin();
+ llvm::ArrayRef<uint8_t> atomContent(singleAtom->rawContent());
+ EXPECT_EQ(0, memcmp(atomContent.data(), contentBytes, contentSize));
+}
OpenPOWER on IntegriCloud