diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2017-05-02 18:30:13 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2017-05-02 18:30:13 +0000 |
commit | a303c417bbdb53703c2c17398b08486bde78f1f6 (patch) | |
tree | 98366d6b93d863cefdc53f16c66c0c5ae7fb2261 /unittests | |
parent | 12f3ca4cdb95b193af905a00e722a4dcb40b3de3 (diff) | |
download | src-test2-a303c417bbdb53703c2c17398b08486bde78f1f6.tar.gz src-test2-a303c417bbdb53703c2c17398b08486bde78f1f6.zip |
Notes
Diffstat (limited to 'unittests')
-rw-r--r-- | unittests/ADT/APIntTest.cpp | 30 | ||||
-rw-r--r-- | unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp | 241 | ||||
-rw-r--r-- | unittests/IR/IRBuilderTest.cpp | 19 | ||||
-rw-r--r-- | unittests/IR/MetadataTest.cpp | 135 | ||||
-rw-r--r-- | unittests/IR/ValueHandleTest.cpp | 80 | ||||
-rw-r--r-- | unittests/Support/BinaryStreamTest.cpp | 18 | ||||
-rw-r--r-- | unittests/Support/CMakeLists.txt | 2 | ||||
-rw-r--r-- | unittests/Support/DynamicLibrary/CMakeLists.txt | 19 | ||||
-rw-r--r-- | unittests/Support/DynamicLibrary/DynamicLibraryTest.cpp | 133 | ||||
-rw-r--r-- | unittests/Support/DynamicLibrary/PipSqueak.cxx | 46 | ||||
-rw-r--r-- | unittests/Support/DynamicLibrary/PipSqueak.h | 19 | ||||
-rw-r--r-- | unittests/Target/AArch64/InstSizes.cpp | 3 |
12 files changed, 634 insertions, 111 deletions
diff --git a/unittests/ADT/APIntTest.cpp b/unittests/ADT/APIntTest.cpp index 2235f271658f..bb6cf35fe9e4 100644 --- a/unittests/ADT/APIntTest.cpp +++ b/unittests/ADT/APIntTest.cpp @@ -1723,21 +1723,21 @@ TEST(APIntTest, getLowBitsSet) { } TEST(APIntTest, getBitsSet) { - APInt i64hi1lo1 = APInt::getBitsSet(64, 63, 1); - EXPECT_EQ(1u, i64hi1lo1.countLeadingOnes()); - EXPECT_EQ(0u, i64hi1lo1.countLeadingZeros()); - EXPECT_EQ(64u, i64hi1lo1.getActiveBits()); - EXPECT_EQ(0u, i64hi1lo1.countTrailingZeros()); - EXPECT_EQ(1u, i64hi1lo1.countTrailingOnes()); - EXPECT_EQ(2u, i64hi1lo1.countPopulation()); - - APInt i127hi1lo1 = APInt::getBitsSet(127, 126, 1); - EXPECT_EQ(1u, i127hi1lo1.countLeadingOnes()); - EXPECT_EQ(0u, i127hi1lo1.countLeadingZeros()); - EXPECT_EQ(127u, i127hi1lo1.getActiveBits()); - EXPECT_EQ(0u, i127hi1lo1.countTrailingZeros()); - EXPECT_EQ(1u, i127hi1lo1.countTrailingOnes()); - EXPECT_EQ(2u, i127hi1lo1.countPopulation()); + APInt i64hi1lo1 = APInt::getBitsSet(64, 1, 63); + EXPECT_EQ(0u, i64hi1lo1.countLeadingOnes()); + EXPECT_EQ(1u, i64hi1lo1.countLeadingZeros()); + EXPECT_EQ(63u, i64hi1lo1.getActiveBits()); + EXPECT_EQ(1u, i64hi1lo1.countTrailingZeros()); + EXPECT_EQ(0u, i64hi1lo1.countTrailingOnes()); + EXPECT_EQ(62u, i64hi1lo1.countPopulation()); + + APInt i127hi1lo1 = APInt::getBitsSet(127, 1, 126); + EXPECT_EQ(0u, i127hi1lo1.countLeadingOnes()); + EXPECT_EQ(1u, i127hi1lo1.countLeadingZeros()); + EXPECT_EQ(126u, i127hi1lo1.getActiveBits()); + EXPECT_EQ(1u, i127hi1lo1.countTrailingZeros()); + EXPECT_EQ(0u, i127hi1lo1.countTrailingOnes()); + EXPECT_EQ(125u, i127hi1lo1.countPopulation()); } TEST(APIntTest, getHighBitsSet) { diff --git a/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp b/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp index 2078e3a96a84..3f0e3dab72bd 100644 --- a/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp +++ b/unittests/DebugInfo/DWARF/DWARFDebugInfoTest.cpp @@ -1667,4 +1667,245 @@ TEST(DWARFDebugInfo, TestImplicitConstAbbrevs) { EXPECT_EQ(DIEs.find(Val2)->second, AbbrevPtrVal2); } +TEST(DWARFDebugInfo, TestDwarfVerifyInvalidCURef) { + // Create a single compile unit with a single function that has a DW_AT_type + // that is CU relative. The CU offset is not valid becuase it is larger than + // the compile unit itself. + + const char *yamldata = R"( + debug_str: + - '' + - /tmp/main.c + - main + debug_abbrev: + - Code: 0x00000001 + Tag: DW_TAG_compile_unit + Children: DW_CHILDREN_yes + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Code: 0x00000002 + Tag: DW_TAG_subprogram + Children: DW_CHILDREN_no + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Attribute: DW_AT_type + Form: DW_FORM_ref4 + debug_info: + - Length: + TotalLength: 22 + Version: 4 + AbbrOffset: 0 + AddrSize: 8 + Entries: + - AbbrCode: 0x00000001 + Values: + - Value: 0x0000000000000001 + - AbbrCode: 0x00000002 + Values: + - Value: 0x000000000000000D + - Value: 0x0000000000001234 + - AbbrCode: 0x00000000 + Values: + )"; + auto ErrOrSections = DWARFYAML::EmitDebugSections(StringRef(yamldata)); + ASSERT_TRUE((bool)ErrOrSections); + + auto &DebugSections = *ErrOrSections; + + DWARFContextInMemory DwarfContext(DebugSections, 8); + + std::string str; + raw_string_ostream strm(str); + EXPECT_FALSE(DwarfContext.verify(strm, DIDT_All)); + const char *err = "error: DW_FORM_ref4 CU offset 0x00001234 is invalid " + "(must be less than CU size of 0x0000001a):"; + EXPECT_TRUE(strm.str().find(err) != std::string::npos); +} + +TEST(DWARFDebugInfo, TestDwarfVerifyInvalidRefAddr) { + // Create a single compile unit with a single function that has an invalid + // DW_AT_type with an invalid .debug_info offset in its DW_FORM_ref_addr. + const char *yamldata = R"( + debug_str: + - '' + - /tmp/main.c + - main + debug_abbrev: + - Code: 0x00000001 + Tag: DW_TAG_compile_unit + Children: DW_CHILDREN_yes + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Code: 0x00000002 + Tag: DW_TAG_subprogram + Children: DW_CHILDREN_no + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Attribute: DW_AT_type + Form: DW_FORM_ref_addr + debug_info: + - Length: + TotalLength: 22 + Version: 4 + AbbrOffset: 0 + AddrSize: 8 + Entries: + - AbbrCode: 0x00000001 + Values: + - Value: 0x0000000000000001 + - AbbrCode: 0x00000002 + Values: + - Value: 0x000000000000000D + - Value: 0x0000000000001234 + - AbbrCode: 0x00000000 + Values: + )"; + auto ErrOrSections = DWARFYAML::EmitDebugSections(StringRef(yamldata)); + ASSERT_TRUE((bool)ErrOrSections); + + auto &DebugSections = *ErrOrSections; + + DWARFContextInMemory DwarfContext(DebugSections, 8); + + std::string str; + raw_string_ostream strm(str); + EXPECT_FALSE(DwarfContext.verify(strm, DIDT_All)); + strm.flush(); + const char *err = "error: DW_FORM_ref_addr offset beyond .debug_info bounds:"; + EXPECT_TRUE(strm.str().find(err) != std::string::npos); +} + +TEST(DWARFDebugInfo, TestDwarfVerifyInvalidRanges) { + // Create a single compile unit with a DW_AT_ranges whose section offset + // isn't valid. + const char *yamldata = R"( + debug_str: + - '' + - /tmp/main.c + debug_abbrev: + - Code: 0x00000001 + Tag: DW_TAG_compile_unit + Children: DW_CHILDREN_no + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Attribute: DW_AT_ranges + Form: DW_FORM_sec_offset + debug_info: + - Length: + TotalLength: 16 + Version: 4 + AbbrOffset: 0 + AddrSize: 8 + Entries: + - AbbrCode: 0x00000001 + Values: + - Value: 0x0000000000000001 + - Value: 0x0000000000001000 + + )"; + auto ErrOrSections = DWARFYAML::EmitDebugSections(StringRef(yamldata)); + ASSERT_TRUE((bool)ErrOrSections); + + auto &DebugSections = *ErrOrSections; + + DWARFContextInMemory DwarfContext(DebugSections, 8); + + std::string str; + raw_string_ostream strm(str); + EXPECT_FALSE(DwarfContext.verify(strm, DIDT_All)); + strm.flush(); + const char *err = "error: DW_AT_ranges offset is beyond .debug_ranges " + "bounds:"; + EXPECT_TRUE(strm.str().find(err) != std::string::npos); +} + +TEST(DWARFDebugInfo, TestDwarfVerifyInvalidStmtList) { + // Create a single compile unit with a DW_AT_stmt_list whose section offset + // isn't valid. + const char *yamldata = R"( + debug_str: + - '' + - /tmp/main.c + debug_abbrev: + - Code: 0x00000001 + Tag: DW_TAG_compile_unit + Children: DW_CHILDREN_no + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + - Attribute: DW_AT_stmt_list + Form: DW_FORM_sec_offset + debug_info: + - Length: + TotalLength: 16 + Version: 4 + AbbrOffset: 0 + AddrSize: 8 + Entries: + - AbbrCode: 0x00000001 + Values: + - Value: 0x0000000000000001 + - Value: 0x0000000000001000 + + )"; + auto ErrOrSections = DWARFYAML::EmitDebugSections(StringRef(yamldata)); + ASSERT_TRUE((bool)ErrOrSections); + + auto &DebugSections = *ErrOrSections; + + DWARFContextInMemory DwarfContext(DebugSections, 8); + + std::string str; + raw_string_ostream strm(str); + EXPECT_FALSE(DwarfContext.verify(strm, DIDT_All)); + strm.flush(); + const char *err = "error: DW_AT_stmt_list offset is beyond .debug_line " + "bounds: 0x00001000"; + EXPECT_TRUE(strm.str().find(err) != std::string::npos); +} + +TEST(DWARFDebugInfo, TestDwarfVerifyInvalidStrp) { + // Create a single compile unit with a single function that has an invalid + // DW_FORM_strp for the DW_AT_name. + const char *yamldata = R"( + debug_str: + - '' + debug_abbrev: + - Code: 0x00000001 + Tag: DW_TAG_compile_unit + Children: DW_CHILDREN_no + Attributes: + - Attribute: DW_AT_name + Form: DW_FORM_strp + debug_info: + - Length: + TotalLength: 12 + Version: 4 + AbbrOffset: 0 + AddrSize: 8 + Entries: + - AbbrCode: 0x00000001 + Values: + - Value: 0x0000000000001234 + )"; + auto ErrOrSections = DWARFYAML::EmitDebugSections(StringRef(yamldata)); + ASSERT_TRUE((bool)ErrOrSections); + + auto &DebugSections = *ErrOrSections; + + DWARFContextInMemory DwarfContext(DebugSections, 8); + + std::string str; + raw_string_ostream strm(str); + EXPECT_FALSE(DwarfContext.verify(strm, DIDT_All)); + strm.flush(); + const char *err = "error: DW_FORM_strp offset beyond .debug_str bounds:"; + EXPECT_TRUE(strm.str().find(err) != std::string::npos); +} + } // end anonymous namespace diff --git a/unittests/IR/IRBuilderTest.cpp b/unittests/IR/IRBuilderTest.cpp index 830ae9587691..5686c3b2b3a7 100644 --- a/unittests/IR/IRBuilderTest.cpp +++ b/unittests/IR/IRBuilderTest.cpp @@ -356,6 +356,25 @@ TEST_F(IRBuilderTest, RAIIHelpersTest) { EXPECT_EQ(BB, Builder.GetInsertBlock()); } +TEST_F(IRBuilderTest, createFunction) { + IRBuilder<> Builder(BB); + DIBuilder DIB(*M); + auto File = DIB.createFile("error.swift", "/"); + auto CU = + DIB.createCompileUnit(dwarf::DW_LANG_Swift, File, "swiftc", true, "", 0); + auto Type = DIB.createSubroutineType(DIB.getOrCreateTypeArray(None)); + auto NoErr = DIB.createFunction(CU, "noerr", "", File, 1, Type, false, true, 1, + DINode::FlagZero, true); + EXPECT_TRUE(!NoErr->getThrownTypes()); + auto Int = DIB.createBasicType("Int", 64, dwarf::DW_ATE_signed); + auto Error = DIB.getOrCreateArray({Int}); + auto Err = + DIB.createFunction(CU, "err", "", File, 1, Type, false, true, 1, + DINode::FlagZero, true, nullptr, nullptr, Error.get()); + EXPECT_TRUE(Err->getThrownTypes().get() == Error.get()); + DIB.finalize(); +} + TEST_F(IRBuilderTest, DIBuilder) { IRBuilder<> Builder(BB); DIBuilder DIB(*M); diff --git a/unittests/IR/MetadataTest.cpp b/unittests/IR/MetadataTest.cpp index 103ba4c92ddf..e61e649df191 100644 --- a/unittests/IR/MetadataTest.cpp +++ b/unittests/IR/MetadataTest.cpp @@ -1512,13 +1512,14 @@ TEST_F(DISubprogramTest, get) { MDTuple *TemplateParams = getTuple(); DISubprogram *Declaration = getSubprogram(); MDTuple *Variables = getTuple(); + MDTuple *ThrownTypes = getTuple(); DICompileUnit *Unit = getUnit(); - auto *N = DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, IsLocalToUnit, IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables); + auto *N = DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, + IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, + ThisAdjustment, Flags, IsOptimized, Unit, TemplateParams, Declaration, + Variables, ThrownTypes); EXPECT_EQ(dwarf::DW_TAG_subprogram, N->getTag()); EXPECT_EQ(Scope, N->getScope()); @@ -1540,98 +1541,109 @@ TEST_F(DISubprogramTest, get) { EXPECT_EQ(TemplateParams, N->getTemplateParams().get()); EXPECT_EQ(Declaration, N->getDeclaration()); EXPECT_EQ(Variables, N->getVariables().get()); - EXPECT_EQ(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, IsLocalToUnit, IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + EXPECT_EQ(ThrownTypes, N->getThrownTypes().get()); + EXPECT_EQ(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get( Context, getCompositeType(), Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get( Context, Scope, "other", LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); - EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, "other", File, Line, - Type, IsLocalToUnit, IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, "other", File, Line, Type, + IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get( Context, Scope, Name, LinkageName, getFile(), Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get( Context, Scope, Name, LinkageName, File, Line + 1, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); - EXPECT_NE(N, - DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - getSubroutineType(), IsLocalToUnit, IsDefinition, - ScopeLine, ContainingType, Virtuality, - VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, !IsLocalToUnit, IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); - EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, IsLocalToUnit, !IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + getSubroutineType(), IsLocalToUnit, + IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, + Flags, IsOptimized, Unit, TemplateParams, + Declaration, Variables, ThrownTypes)); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + !IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + IsLocalToUnit, !IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get( Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine + 1, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, - Unit, TemplateParams, Declaration, Variables)); - EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, IsLocalToUnit, IsDefinition, ScopeLine, - getCompositeType(), Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + IsLocalToUnit, IsDefinition, ScopeLine, getCompositeType(), + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality + 1, VirtualIndex, ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + TemplateParams, Declaration, Variables, + ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex + 1, ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + TemplateParams, Declaration, Variables, + ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, !IsOptimized, Unit, - TemplateParams, Declaration, Variables)); + TemplateParams, Declaration, Variables, + ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, nullptr, - TemplateParams, Declaration, Variables)); - EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, - Type, IsLocalToUnit, IsDefinition, ScopeLine, - ContainingType, Virtuality, VirtualIndex, - ThisAdjustment, Flags, IsOptimized, Unit, - getTuple(), Declaration, Variables)); + TemplateParams, Declaration, Variables, + ThrownTypes)); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, getTuple(), Declaration, Variables, ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, Unit, - TemplateParams, getSubprogram(), Variables)); + TemplateParams, getSubprogram(), Variables, + ThrownTypes)); EXPECT_NE(N, DISubprogram::get(Context, Scope, Name, LinkageName, File, Line, Type, IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, Unit, TemplateParams, Declaration, getTuple())); + EXPECT_NE(N, DISubprogram::get( + Context, Scope, Name, LinkageName, File, Line, Type, + IsLocalToUnit, IsDefinition, ScopeLine, ContainingType, + Virtuality, VirtualIndex, ThisAdjustment, Flags, IsOptimized, + Unit, TemplateParams, Declaration, Variables, getTuple())); TempDISubprogram Temp = N->clone(); EXPECT_EQ(N, MDNode::replaceWithUniqued(std::move(Temp))); @@ -1720,31 +1732,18 @@ typedef MetadataTest DINamespaceTest; TEST_F(DINamespaceTest, get) { DIScope *Scope = getFile(); - DIFile *File = getFile(); StringRef Name = "namespace"; - unsigned Line = 5; bool ExportSymbols = true; - auto *N = DINamespace::get(Context, Scope, File, Name, Line, ExportSymbols); + auto *N = DINamespace::get(Context, Scope, Name, ExportSymbols); EXPECT_EQ(dwarf::DW_TAG_namespace, N->getTag()); EXPECT_EQ(Scope, N->getScope()); - EXPECT_EQ(File, N->getFile()); EXPECT_EQ(Name, N->getName()); - EXPECT_EQ(Line, N->getLine()); - EXPECT_EQ(N, - DINamespace::get(Context, Scope, File, Name, Line, ExportSymbols)); - - EXPECT_NE(N, - DINamespace::get(Context, getFile(), File, Name, Line, ExportSymbols)); - EXPECT_NE(N, - DINamespace::get(Context, Scope, getFile(), Name, Line, ExportSymbols)); - EXPECT_NE(N, - DINamespace::get(Context, Scope, File, "other", Line, ExportSymbols)); - EXPECT_NE(N, - DINamespace::get(Context, Scope, File, Name, Line + 1, ExportSymbols)); - EXPECT_NE(N, - DINamespace::get(Context, Scope, File, Name, Line, !ExportSymbols)); + EXPECT_EQ(N, DINamespace::get(Context, Scope, Name, ExportSymbols)); + EXPECT_NE(N, DINamespace::get(Context, getFile(), Name, ExportSymbols)); + EXPECT_NE(N, DINamespace::get(Context, Scope, "other", ExportSymbols)); + EXPECT_NE(N, DINamespace::get(Context, Scope, Name, !ExportSymbols)); TempDINamespace Temp = N->clone(); EXPECT_EQ(N, MDNode::replaceWithUniqued(std::move(Temp))); diff --git a/unittests/IR/ValueHandleTest.cpp b/unittests/IR/ValueHandleTest.cpp index 1abc87c2fdc7..9a4ce156dc3d 100644 --- a/unittests/IR/ValueHandleTest.cpp +++ b/unittests/IR/ValueHandleTest.cpp @@ -44,11 +44,29 @@ TEST_F(ValueHandle, WeakVH_BasicOperation) { // doesn't matter which method. EXPECT_EQ(Type::getInt32Ty(Context), WVH->getType()); EXPECT_EQ(Type::getInt32Ty(Context), (*WVH).getType()); + + WVH = BitcastV.get(); + BitcastV->replaceAllUsesWith(ConstantV); + EXPECT_EQ(WVH, BitcastV.get()); + BitcastV.reset(); + EXPECT_EQ(WVH, nullptr); +} + +TEST_F(ValueHandle, WeakTrackingVH_BasicOperation) { + WeakTrackingVH WVH(BitcastV.get()); + EXPECT_EQ(BitcastV.get(), WVH); + WVH = ConstantV; + EXPECT_EQ(ConstantV, WVH); + + // Make sure I can call a method on the underlying Value. It + // doesn't matter which method. + EXPECT_EQ(Type::getInt32Ty(Context), WVH->getType()); + EXPECT_EQ(Type::getInt32Ty(Context), (*WVH).getType()); } -TEST_F(ValueHandle, WeakVH_Comparisons) { - WeakVH BitcastWVH(BitcastV.get()); - WeakVH ConstantWVH(ConstantV); +TEST_F(ValueHandle, WeakTrackingVH_Comparisons) { + WeakTrackingVH BitcastWVH(BitcastV.get()); + WeakTrackingVH ConstantWVH(ConstantV); EXPECT_TRUE(BitcastWVH == BitcastWVH); EXPECT_TRUE(BitcastV.get() == BitcastWVH); @@ -79,20 +97,20 @@ TEST_F(ValueHandle, WeakVH_Comparisons) { EXPECT_EQ(BV >= CV, BitcastWVH >= ConstantV); } -TEST_F(ValueHandle, WeakVH_FollowsRAUW) { - WeakVH WVH(BitcastV.get()); - WeakVH WVH_Copy(WVH); - WeakVH WVH_Recreated(BitcastV.get()); +TEST_F(ValueHandle, WeakTrackingVH_FollowsRAUW) { + WeakTrackingVH WVH(BitcastV.get()); + WeakTrackingVH WVH_Copy(WVH); + WeakTrackingVH WVH_Recreated(BitcastV.get()); BitcastV->replaceAllUsesWith(ConstantV); EXPECT_EQ(ConstantV, WVH); EXPECT_EQ(ConstantV, WVH_Copy); EXPECT_EQ(ConstantV, WVH_Recreated); } -TEST_F(ValueHandle, WeakVH_NullOnDeletion) { - WeakVH WVH(BitcastV.get()); - WeakVH WVH_Copy(WVH); - WeakVH WVH_Recreated(BitcastV.get()); +TEST_F(ValueHandle, WeakTrackingVH_NullOnDeletion) { + WeakTrackingVH WVH(BitcastV.get()); + WeakTrackingVH WVH_Copy(WVH); + WeakTrackingVH WVH_Recreated(BitcastV.get()); BitcastV.reset(); Value *null_value = nullptr; EXPECT_EQ(null_value, WVH); @@ -343,11 +361,11 @@ TEST_F(ValueHandle, DestroyingOtherVHOnSameValueDoesntBreakIteration) { class DestroyingVH final : public CallbackVH { public: - std::unique_ptr<WeakVH> ToClear[2]; + std::unique_ptr<WeakTrackingVH> ToClear[2]; DestroyingVH(Value *V) { - ToClear[0].reset(new WeakVH(V)); + ToClear[0].reset(new WeakTrackingVH(V)); setValPtr(V); - ToClear[1].reset(new WeakVH(V)); + ToClear[1].reset(new WeakTrackingVH(V)); } void deleted() override { ToClear[0].reset(); @@ -361,9 +379,9 @@ TEST_F(ValueHandle, DestroyingOtherVHOnSameValueDoesntBreakIteration) { }; { - WeakVH ShouldBeVisited1(BitcastV.get()); + WeakTrackingVH ShouldBeVisited1(BitcastV.get()); DestroyingVH C(BitcastV.get()); - WeakVH ShouldBeVisited2(BitcastV.get()); + WeakTrackingVH ShouldBeVisited2(BitcastV.get()); BitcastV->replaceAllUsesWith(ConstantV); EXPECT_EQ(ConstantV, static_cast<Value*>(ShouldBeVisited1)); @@ -371,9 +389,9 @@ TEST_F(ValueHandle, DestroyingOtherVHOnSameValueDoesntBreakIteration) { } { - WeakVH ShouldBeVisited1(BitcastV.get()); + WeakTrackingVH ShouldBeVisited1(BitcastV.get()); DestroyingVH C(BitcastV.get()); - WeakVH ShouldBeVisited2(BitcastV.get()); + WeakTrackingVH ShouldBeVisited2(BitcastV.get()); BitcastV.reset(); EXPECT_EQ(nullptr, static_cast<Value*>(ShouldBeVisited1)); @@ -482,6 +500,12 @@ TEST_F(ValueHandle, PoisoningVH_ReducesToPointer) { #else // !NDEBUG +TEST_F(ValueHandle, TrackingVH_Tracks) { + TrackingVH<Value> VH(BitcastV.get()); + BitcastV->replaceAllUsesWith(ConstantV); + EXPECT_EQ(VH, ConstantV); +} + #ifdef GTEST_HAS_DEATH_TEST TEST_F(ValueHandle, PoisoningVH_Asserts) { @@ -502,6 +526,26 @@ TEST_F(ValueHandle, PoisoningVH_Asserts) { // Don't clear anything out here as destroying the handles should be fine. } +TEST_F(ValueHandle, TrackingVH_Asserts) { + { + TrackingVH<Value> VH(BitcastV.get()); + + // The tracking handle shouldn't assert when the value is deleted. + BitcastV.reset(new BitCastInst(ConstantV, Type::getInt32Ty(Context))); + // But should when we access the handle. + EXPECT_DEATH((void)*VH, + "TrackingVH must be non-null and valid on dereference!"); + } + + { + TrackingVH<Instruction> VH(BitcastV.get()); + + BitcastV->replaceAllUsesWith(ConstantV); + EXPECT_DEATH((void)*VH, + "Tracked Value was replaced by one with an invalid type!"); + } +} + #endif // GTEST_HAS_DEATH_TEST #endif // NDEBUG diff --git a/unittests/Support/BinaryStreamTest.cpp b/unittests/Support/BinaryStreamTest.cpp index 1e646a6cf900..74c51e382d99 100644 --- a/unittests/Support/BinaryStreamTest.cpp +++ b/unittests/Support/BinaryStreamTest.cpp @@ -358,12 +358,14 @@ TEST_F(BinaryStreamTest, VarStreamArray) { struct StringExtractor { public: - Error operator()(BinaryStreamRef Stream, uint32_t &Len, StringRef &Item) { - if (Index == 0) + typedef uint32_t ContextType; + static Error extract(BinaryStreamRef Stream, uint32_t &Len, StringRef &Item, + uint32_t *Index) { + if (*Index == 0) Len = strlen("1. Test"); - else if (Index == 1) + else if (*Index == 1) Len = strlen("2. Longer Test"); - else if (Index == 2) + else if (*Index == 2) Len = strlen("3. Really Long Test"); else Len = strlen("4. Super Extra Longest Test Of All"); @@ -372,16 +374,14 @@ TEST_F(BinaryStreamTest, VarStreamArray) { return EC; Item = StringRef(reinterpret_cast<const char *>(Bytes.data()), Bytes.size()); - ++Index; + ++(*Index); return Error::success(); } - - private: - uint32_t Index = 0; }; for (auto &Stream : Streams) { - VarStreamArray<StringRef, StringExtractor> Array(*Stream.Input); + uint32_t Context = 0; + VarStreamArray<StringRef, StringExtractor> Array(*Stream.Input, &Context); auto Iter = Array.begin(); ASSERT_EQ("1. Test", *Iter++); ASSERT_EQ("2. Longer Test", *Iter++); diff --git a/unittests/Support/CMakeLists.txt b/unittests/Support/CMakeLists.txt index a7be18b6a3c5..1f677100dcef 100644 --- a/unittests/Support/CMakeLists.txt +++ b/unittests/Support/CMakeLists.txt @@ -67,3 +67,5 @@ add_llvm_unittest(SupportTests # ManagedStatic.cpp uses <pthread>. target_link_libraries(SupportTests ${LLVM_PTHREAD_LIB}) + +add_subdirectory(DynamicLibrary) diff --git a/unittests/Support/DynamicLibrary/CMakeLists.txt b/unittests/Support/DynamicLibrary/CMakeLists.txt new file mode 100644 index 000000000000..f0e945e78b18 --- /dev/null +++ b/unittests/Support/DynamicLibrary/CMakeLists.txt @@ -0,0 +1,19 @@ +set(LLVM_LINK_COMPONENTS Support) + +add_llvm_unittest(DynamicLibraryTests DynamicLibraryTest.cpp) + +export_executable_symbols(DynamicLibraryTests) + +add_library(PipSqueak SHARED PipSqueak.cxx) + +set_output_directory(PipSqueak + BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_CFG_INTDIR} + LIBRARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_CFG_INTDIR} + ) + +set_target_properties(PipSqueak + PROPERTIES PREFIX "" + SUFFIX ".so" + ) + +add_dependencies(DynamicLibraryTests PipSqueak) diff --git a/unittests/Support/DynamicLibrary/DynamicLibraryTest.cpp b/unittests/Support/DynamicLibrary/DynamicLibraryTest.cpp new file mode 100644 index 000000000000..d46eadc9a046 --- /dev/null +++ b/unittests/Support/DynamicLibrary/DynamicLibraryTest.cpp @@ -0,0 +1,133 @@ +//===- llvm/unittest/Support/DynamicLibrary/DynamicLibraryTest.cpp --------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "llvm/Config/config.h" +#include "llvm/Support/DynamicLibrary.h" +#include "llvm/Support/FileSystem.h" +#include "llvm/Support/ManagedStatic.h" +#include "llvm/Support/Path.h" +#include "gtest/gtest.h" + +#include "PipSqueak.h" +#include <string> + +using namespace llvm; +using namespace llvm::sys; + +extern "C" PIPSQUEAK_EXPORT const char *TestA() { return "ProcessCall"; } + +std::string LibPath() { + void *Ptr = (void*)(intptr_t)TestA; + std::string Path = fs::getMainExecutable("DynamicLibraryTests", Ptr); + llvm::SmallString<256> Buf(path::parent_path(Path)); + path::append(Buf, "PipSqueak.so"); + return Buf.str(); +} + +#if defined(_WIN32) || (defined(HAVE_DLFCN_H) && defined(HAVE_DLOPEN)) + +typedef void (*SetStrings)(std::string &GStr, std::string &LStr); +typedef const char *(*GetString)(); + +template <class T> static T FuncPtr(void *Ptr) { + union { + T F; + void *P; + } Tmp; + Tmp.P = Ptr; + return Tmp.F; +} +template <class T> static void* PtrFunc(T *Func) { + union { + T *F; + void *P; + } Tmp; + Tmp.F = Func; + return Tmp.P; +} + +static const char *OverloadTestA() { return "OverloadCall"; } + +std::string StdString(const char *Ptr) { return Ptr ? Ptr : ""; } + +TEST(DynamicLibrary, Overload) { + { + std::string Err; + llvm_shutdown_obj Shutdown; + DynamicLibrary DL = + DynamicLibrary::getPermanentLibrary(LibPath().c_str(), &Err); + EXPECT_TRUE(DL.isValid()); + EXPECT_TRUE(Err.empty()); + + GetString GS = FuncPtr<GetString>(DL.getAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS != &TestA); + EXPECT_EQ(StdString(GS()), "LibCall"); + + GS = FuncPtr<GetString>(DynamicLibrary::SearchForAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS != &TestA); + EXPECT_EQ(StdString(GS()), "LibCall"); + + DL = DynamicLibrary::getPermanentLibrary(nullptr, &Err); + EXPECT_TRUE(DL.isValid()); + EXPECT_TRUE(Err.empty()); + + GS = FuncPtr<GetString>(DynamicLibrary::SearchForAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS == &TestA); + EXPECT_EQ(StdString(GS()), "ProcessCall"); + + GS = FuncPtr<GetString>(DL.getAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS == &TestA); + EXPECT_EQ(StdString(GS()), "ProcessCall"); + + DynamicLibrary::AddSymbol("TestA", PtrFunc(&OverloadTestA)); + GS = FuncPtr<GetString>(DL.getAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS != &OverloadTestA); + + GS = FuncPtr<GetString>(DynamicLibrary::SearchForAddressOfSymbol("TestA")); + EXPECT_TRUE(GS != nullptr && GS == &OverloadTestA); + EXPECT_EQ(StdString(GS()), "OverloadCall"); + } + EXPECT_TRUE(FuncPtr<GetString>(DynamicLibrary::SearchForAddressOfSymbol( + "TestA")) == nullptr); +} + +TEST(DynamicLibrary, Shutdown) { + std::string A, B; + { + std::string Err; + llvm_shutdown_obj Shutdown; + DynamicLibrary DL = + DynamicLibrary::getPermanentLibrary(LibPath().c_str(), &Err); + EXPECT_TRUE(DL.isValid()); + EXPECT_TRUE(Err.empty()); + + SetStrings SS = FuncPtr<SetStrings>( + DynamicLibrary::SearchForAddressOfSymbol("SetStrings")); + EXPECT_TRUE(SS != nullptr); + + SS(A, B); + EXPECT_EQ(B, "Local::Local"); + } + EXPECT_EQ(A, "Global::~Global"); + EXPECT_EQ(B, "Local::~Local"); + EXPECT_TRUE(FuncPtr<SetStrings>(DynamicLibrary::SearchForAddressOfSymbol( + "SetStrings")) == nullptr); +} + +#else + +TEST(DynamicLibrary, Unsupported) { + std::string Err; + DynamicLibrary DL = + DynamicLibrary::getPermanentLibrary(LibPath().c_str(), &Err); + EXPECT_FALSE(DL.isValid()); + EXPECT_EQ(Err, "dlopen() not supported on this platform"); +} + +#endif diff --git a/unittests/Support/DynamicLibrary/PipSqueak.cxx b/unittests/Support/DynamicLibrary/PipSqueak.cxx new file mode 100644 index 000000000000..d1cf7c042b72 --- /dev/null +++ b/unittests/Support/DynamicLibrary/PipSqueak.cxx @@ -0,0 +1,46 @@ +//===- llvm/unittest/Support/DynamicLibrary/PipSqueak.cxx -----------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "PipSqueak.h" + +#if defined(_WIN32) && !defined(__GNUC__) +// Disable warnings from inclusion of xlocale & exception +#pragma warning(push) +#pragma warning(disable: 4530) +#pragma warning(disable: 4577) +#include <string> +#pragma warning(pop) +#else +#include <string> +#endif + +struct Global { + std::string *Str; + Global() : Str(nullptr) {} + ~Global() { + if (Str) + *Str = "Global::~Global"; + } +}; + +struct Local { + std::string &Str; + Local(std::string &S) : Str(S) { Str = "Local::Local"; } + ~Local() { Str = "Local::~Local"; } +}; + +static Global Glb; + +extern "C" PIPSQUEAK_EXPORT void SetStrings(std::string &GStr, + std::string &LStr) { + static Local Lcl(LStr); + Glb.Str = &GStr; +} + +extern "C" PIPSQUEAK_EXPORT const char *TestA() { return "LibCall"; } diff --git a/unittests/Support/DynamicLibrary/PipSqueak.h b/unittests/Support/DynamicLibrary/PipSqueak.h new file mode 100644 index 000000000000..e6a859d60716 --- /dev/null +++ b/unittests/Support/DynamicLibrary/PipSqueak.h @@ -0,0 +1,19 @@ +//===- llvm/unittest/Support/DynamicLibrary/PipSqueak.h -------------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_PIPSQUEAK_H +#define LLVM_PIPSQUEAK_H + +#ifdef _WIN32 +#define PIPSQUEAK_EXPORT __declspec(dllexport) +#else +#define PIPSQUEAK_EXPORT +#endif + +#endif diff --git a/unittests/Target/AArch64/InstSizes.cpp b/unittests/Target/AArch64/InstSizes.cpp index 22b47c6852ab..5adbd7d2de43 100644 --- a/unittests/Target/AArch64/InstSizes.cpp +++ b/unittests/Target/AArch64/InstSizes.cpp @@ -30,7 +30,8 @@ std::unique_ptr<TargetMachine> createTargetMachine() { std::unique_ptr<AArch64InstrInfo> createInstrInfo(TargetMachine *TM) { AArch64Subtarget ST(TM->getTargetTriple(), TM->getTargetCPU(), - TM->getTargetFeatureString(), *TM, /* isLittle */ false); + TM->getTargetFeatureString(), *TM, /* isLittle */ false, + /* ForCodeSize */ false); return llvm::make_unique<AArch64InstrInfo>(ST); } |