aboutsummaryrefslogtreecommitdiff
path: root/unittests/MC
diff options
context:
space:
mode:
Diffstat (limited to 'unittests/MC')
-rw-r--r--unittests/MC/CMakeLists.txt3
-rw-r--r--unittests/MC/DwarfLineTables.cpp179
-rw-r--r--unittests/MC/Makefile15
-rw-r--r--unittests/MC/StringTableBuilderTest.cpp23
-rw-r--r--unittests/MC/TargetRegistry.cpp46
-rw-r--r--unittests/MC/YAMLTest.cpp38
6 files changed, 250 insertions, 54 deletions
diff --git a/unittests/MC/CMakeLists.txt b/unittests/MC/CMakeLists.txt
index f83eaf4779f9..c760c0267a9c 100644
--- a/unittests/MC/CMakeLists.txt
+++ b/unittests/MC/CMakeLists.txt
@@ -7,6 +7,7 @@ set(LLVM_LINK_COMPONENTS
add_llvm_unittest(MCTests
Disassembler.cpp
+ DwarfLineTables.cpp
StringTableBuilderTest.cpp
- YAMLTest.cpp
+ TargetRegistry.cpp
)
diff --git a/unittests/MC/DwarfLineTables.cpp b/unittests/MC/DwarfLineTables.cpp
new file mode 100644
index 000000000000..4bfb5acea039
--- /dev/null
+++ b/unittests/MC/DwarfLineTables.cpp
@@ -0,0 +1,179 @@
+//===- llvm/unittest/MC/DwarfLineTables.cpp ------------------------------===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm/Support/Dwarf.h"
+#include "llvm/ADT/STLExtras.h"
+#include "llvm/MC/MCAsmInfo.h"
+#include "llvm/MC/MCContext.h"
+#include "llvm/MC/MCDwarf.h"
+#include "llvm/MC/MCRegisterInfo.h"
+#include "llvm/Support/TargetRegistry.h"
+#include "llvm/Support/TargetSelect.h"
+#include "gtest/gtest.h"
+
+using namespace llvm;
+
+namespace {
+struct Context {
+ const char *Triple = "x86_64-pc-linux";
+ std::unique_ptr<MCRegisterInfo> MRI;
+ std::unique_ptr<MCAsmInfo> MAI;
+ std::unique_ptr<MCContext> Ctx;
+
+ Context() {
+ llvm::InitializeAllTargetInfos();
+ llvm::InitializeAllTargetMCs();
+ llvm::InitializeAllDisassemblers();
+
+ // If we didn't build x86, do not run the test.
+ std::string Error;
+ const Target *TheTarget = TargetRegistry::lookupTarget(Triple, Error);
+ if (!TheTarget)
+ return;
+
+ MRI.reset(TheTarget->createMCRegInfo(Triple));
+ MAI.reset(TheTarget->createMCAsmInfo(*MRI, Triple));
+ Ctx = llvm::make_unique<MCContext>(MAI.get(), MRI.get(), nullptr);
+ }
+
+ operator bool() { return Ctx.get(); }
+ operator MCContext &() { return *Ctx; };
+};
+
+Context Ctxt;
+}
+
+void verifyEncoding(MCDwarfLineTableParams Params, int LineDelta, int AddrDelta,
+ ArrayRef<uint8_t> ExpectedEncoding) {
+ SmallString<16> Buffer;
+ raw_svector_ostream EncodingOS(Buffer);
+ MCDwarfLineAddr::Encode(Ctxt, Params, LineDelta, AddrDelta, EncodingOS);
+ ArrayRef<uint8_t> Encoding(reinterpret_cast<uint8_t *>(Buffer.data()),
+ Buffer.size());
+ EXPECT_EQ(ExpectedEncoding, Encoding);
+}
+
+TEST(DwarfLineTables, TestDefaultParams) {
+ if (!Ctxt)
+ return;
+
+ MCDwarfLineTableParams Params;
+
+ // Minimal line offset expressible through extended opcode, 0 addr delta
+ const uint8_t Encoding0[] = {13}; // Special opcode Addr += 0, Line += -5
+ verifyEncoding(Params, -5, 0, Encoding0);
+
+ // Maximal line offset expressible through extended opcode,
+ const uint8_t Encoding1[] = {26}; // Special opcode Addr += 0, Line += +8
+ verifyEncoding(Params, 8, 0, Encoding1);
+
+ // Random value in the middle of the special ocode range
+ const uint8_t Encoding2[] = {146}; // Special opcode Addr += 9, Line += 2
+ verifyEncoding(Params, 2, 9, Encoding2);
+
+ // Minimal line offset expressible through extended opcode, max addr delta
+ const uint8_t Encoding3[] = {251}; // Special opcode Addr += 17, Line += -5
+ verifyEncoding(Params, -5, 17, Encoding3);
+
+ // Biggest special opcode
+ const uint8_t Encoding4[] = {255}; // Special opcode Addr += 17, Line += -1
+ verifyEncoding(Params, -1, 17, Encoding4);
+
+ // Line delta outside of the special opcode range, address delta in range
+ const uint8_t Encoding5[] = {dwarf::DW_LNS_advance_line, 9,
+ 158}; // Special opcode Addr += 10, Line += 0
+ verifyEncoding(Params, 9, 10, Encoding5);
+
+ // Address delta outside of the special opcode range, but small
+ // enough to do DW_LNS_const_add_pc + special opcode.
+ const uint8_t Encoding6[] = {dwarf::DW_LNS_const_add_pc, // pc += 17
+ 62}; // Special opcode Addr += 3, Line += 2
+ verifyEncoding(Params, 2, 20, Encoding6);
+
+ // Address delta big enough to require the use of DW_LNS_advance_pc
+ // Line delta in special opcode range
+ const uint8_t Encoding7[] = {dwarf::DW_LNS_advance_pc, 100,
+ 20}; // Special opcode Addr += 0, Line += 2
+ verifyEncoding(Params, 2, 100, Encoding7);
+
+ // No special opcode possible.
+ const uint8_t Encoding8[] = {dwarf::DW_LNS_advance_line, 20,
+ dwarf::DW_LNS_advance_pc, 100,
+ dwarf::DW_LNS_copy};
+ verifyEncoding(Params, 20, 100, Encoding8);
+}
+
+TEST(DwarfLineTables, TestCustomParams) {
+ if (!Ctxt)
+ return;
+
+ // Some tests against the example values given in the standard.
+ MCDwarfLineTableParams Params;
+ Params.DWARF2LineOpcodeBase = 13;
+ Params.DWARF2LineBase = -3;
+ Params.DWARF2LineRange = 12;
+
+ // Minimal line offset expressible through extended opcode, 0 addr delta
+ const uint8_t Encoding0[] = {13}; // Special opcode Addr += 0, Line += -5
+ verifyEncoding(Params, -3, 0, Encoding0);
+
+ // Maximal line offset expressible through extended opcode,
+ const uint8_t Encoding1[] = {24}; // Special opcode Addr += 0, Line += +8
+ verifyEncoding(Params, 8, 0, Encoding1);
+
+ // Random value in the middle of the special ocode range
+ const uint8_t Encoding2[] = {126}; // Special opcode Addr += 9, Line += 2
+ verifyEncoding(Params, 2, 9, Encoding2);
+
+ // Minimal line offset expressible through extended opcode, max addr delta
+ const uint8_t Encoding3[] = {253}; // Special opcode Addr += 20, Line += -3
+ verifyEncoding(Params, -3, 20, Encoding3);
+
+ // Biggest special opcode
+ const uint8_t Encoding4[] = {255}; // Special opcode Addr += 17, Line += -1
+ verifyEncoding(Params, -1, 20, Encoding4);
+
+ // Line delta outside of the special opcode range, address delta in range
+ const uint8_t Encoding5[] = {dwarf::DW_LNS_advance_line, 9,
+ 136}; // Special opcode Addr += 10, Line += 0
+ verifyEncoding(Params, 9, 10, Encoding5);
+
+ // Address delta outside of the special opcode range, but small
+ // enough to do DW_LNS_const_add_pc + special opcode.
+ const uint8_t Encoding6[] = {dwarf::DW_LNS_const_add_pc, // pc += 20
+ 138}; // Special opcode Addr += 10, Line += 2
+ verifyEncoding(Params, 2, 30, Encoding6);
+
+ // Address delta big enough to require the use of DW_LNS_advance_pc
+ // Line delta in special opcode range
+ const uint8_t Encoding7[] = {dwarf::DW_LNS_advance_pc, 100,
+ 18}; // Special opcode Addr += 0, Line += 2
+ verifyEncoding(Params, 2, 100, Encoding7);
+
+ // No special opcode possible.
+ const uint8_t Encoding8[] = {dwarf::DW_LNS_advance_line, 20,
+ dwarf::DW_LNS_advance_pc, 100,
+ dwarf::DW_LNS_copy};
+ verifyEncoding(Params, 20, 100, Encoding8);
+}
+
+TEST(DwarfLineTables, TestCustomParams2) {
+ if (!Ctxt)
+ return;
+
+ // Corner case param values.
+ MCDwarfLineTableParams Params;
+ Params.DWARF2LineOpcodeBase = 13;
+ Params.DWARF2LineBase = 1;
+ Params.DWARF2LineRange = 255;
+
+ const uint8_t Encoding0[] = {dwarf::DW_LNS_advance_line, 248, 1,
+ dwarf::DW_LNS_copy};
+ verifyEncoding(Params, 248, 0, Encoding0);
+}
diff --git a/unittests/MC/Makefile b/unittests/MC/Makefile
deleted file mode 100644
index 3f8d1ef9555c..000000000000
--- a/unittests/MC/Makefile
+++ /dev/null
@@ -1,15 +0,0 @@
-##===- unittests/IR/Makefile -------------------------------*- Makefile -*-===##
-#
-# The LLVM Compiler Infrastructure
-#
-# This file is distributed under the University of Illinois Open Source
-# License. See LICENSE.TXT for details.
-#
-##===----------------------------------------------------------------------===##
-
-LEVEL = ../..
-TESTNAME = MC
-LINK_COMPONENTS := all-targets MCDisassembler Object
-
-include $(LEVEL)/Makefile.config
-include $(LLVM_SRC_ROOT)/unittests/Makefile.unittest
diff --git a/unittests/MC/StringTableBuilderTest.cpp b/unittests/MC/StringTableBuilderTest.cpp
index 4cc0bda0a03a..f78d3588ffff 100644
--- a/unittests/MC/StringTableBuilderTest.cpp
+++ b/unittests/MC/StringTableBuilderTest.cpp
@@ -68,4 +68,27 @@ TEST(StringTableBuilderTest, BasicWinCOFF) {
EXPECT_EQ(23U, B.getOffset("river horse"));
}
+TEST(StringTableBuilderTest, ELFInOrder) {
+ StringTableBuilder B(StringTableBuilder::ELF);
+ EXPECT_EQ(1U, B.add("foo"));
+ EXPECT_EQ(5U, B.add("bar"));
+ EXPECT_EQ(9U, B.add("foobar"));
+
+ B.finalizeInOrder();
+
+ std::string Expected;
+ Expected += '\x00';
+ Expected += "foo";
+ Expected += '\x00';
+ Expected += "bar";
+ Expected += '\x00';
+ Expected += "foobar";
+ Expected += '\x00';
+
+ EXPECT_EQ(Expected, B.data());
+ EXPECT_EQ(1U, B.getOffset("foo"));
+ EXPECT_EQ(5U, B.getOffset("bar"));
+ EXPECT_EQ(9U, B.getOffset("foobar"));
+}
+
}
diff --git a/unittests/MC/TargetRegistry.cpp b/unittests/MC/TargetRegistry.cpp
new file mode 100644
index 000000000000..eb46b22f06c1
--- /dev/null
+++ b/unittests/MC/TargetRegistry.cpp
@@ -0,0 +1,46 @@
+//===- unittests/MC/TargetRegistry.cpp ------------------------------------===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+// The target registry code lives in Support, but it relies on linking in all
+// LLVM targets. We keep this test with the MC tests, which already do that, to
+// keep the SupportTests target small.
+
+#include "llvm/Support/TargetRegistry.h"
+#include "llvm/Support/TargetSelect.h"
+#include "gtest/gtest.h"
+
+using namespace llvm;
+
+namespace {
+
+TEST(TargetRegistry, TargetHasArchType) {
+ // Presence of at least one target will be asserted when done with the loop,
+ // else this would pass by accident if InitializeAllTargetInfos were omitted.
+ int Count = 0;
+
+ llvm::InitializeAllTargetInfos();
+
+ for (const Target &T : TargetRegistry::targets()) {
+ StringRef Name = T.getName();
+ // There is really no way (at present) to ask a Target whether it targets
+ // a specific architecture, because the logic for that is buried in a
+ // predicate.
+ // We can't ask the predicate "Are you a function that always returns
+ // false?"
+ // So given that the cpp backend truly has no target arch, it is skipped.
+ if (Name != "cpp") {
+ Triple::ArchType Arch = Triple::getArchTypeForLLVMName(Name);
+ EXPECT_NE(Arch, Triple::UnknownArch);
+ ++Count;
+ }
+ }
+ ASSERT_NE(Count, 0);
+}
+
+} // end namespace
diff --git a/unittests/MC/YAMLTest.cpp b/unittests/MC/YAMLTest.cpp
deleted file mode 100644
index 09709ad73fc7..000000000000
--- a/unittests/MC/YAMLTest.cpp
+++ /dev/null
@@ -1,38 +0,0 @@
-//===- llvm/unittest/Object/YAMLTest.cpp - Tests for Object YAML ----------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-
-#include "llvm/MC/YAML.h"
-#include "llvm/Support/YAMLTraits.h"
-#include "gtest/gtest.h"
-
-using namespace llvm;
-
-struct BinaryHolder {
- yaml::BinaryRef Binary;
-};
-
-namespace llvm {
-namespace yaml {
-template <>
-struct MappingTraits<BinaryHolder> {
- static void mapping(IO &IO, BinaryHolder &BH) {
- IO.mapRequired("Binary", BH.Binary);
- }
-};
-} // end namespace yaml
-} // end namespace llvm
-
-TEST(ObjectYAML, BinaryRef) {
- BinaryHolder BH;
- SmallVector<char, 32> Buf;
- llvm::raw_svector_ostream OS(Buf);
- yaml::Output YOut(OS);
- YOut << BH;
- EXPECT_NE(OS.str().find("''"), StringRef::npos);
-}