summaryrefslogtreecommitdiffstats
path: root/clang/unittests/Format/CleanupTest.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/unittests/Format/CleanupTest.cpp')
-rw-r--r--clang/unittests/Format/CleanupTest.cpp288
1 files changed, 272 insertions, 16 deletions
diff --git a/clang/unittests/Format/CleanupTest.cpp b/clang/unittests/Format/CleanupTest.cpp
index 93cc1e82fe6..9b011e436ac 100644
--- a/clang/unittests/Format/CleanupTest.cpp
+++ b/clang/unittests/Format/CleanupTest.cpp
@@ -243,13 +243,39 @@ TEST_F(CleanupTest, CtorInitializerInNamespace) {
class CleanUpReplacementsTest : public ::testing::Test {
protected:
- tooling::Replacement createReplacement(SourceLocation Start, unsigned Length,
- llvm::StringRef ReplacementText) {
- return tooling::Replacement(Context.Sources, Start, Length,
- ReplacementText);
+ tooling::Replacement createReplacement(unsigned Offset, unsigned Length,
+ StringRef Text) {
+ return tooling::Replacement(FileName, Offset, Length, Text);
}
- RewriterTestContext Context;
+ tooling::Replacement createInsertion(StringRef HeaderName) {
+ return createReplacement(UINT_MAX, 0, HeaderName);
+ }
+
+ inline std::string apply(StringRef Code,
+ const tooling::Replacements Replaces) {
+ return applyAllReplacements(
+ Code, cleanupAroundReplacements(Code, Replaces, Style));
+ }
+
+ inline std::string formatAndApply(StringRef Code,
+ const tooling::Replacements Replaces) {
+ return applyAllReplacements(
+ Code,
+ formatReplacements(
+ Code, cleanupAroundReplacements(Code, Replaces, Style), Style));
+ }
+
+ int getOffset(StringRef Code, int Line, int Column) {
+ RewriterTestContext Context;
+ FileID ID = Context.createInMemoryFile(FileName, Code);
+ auto DecomposedLocation =
+ Context.Sources.getDecomposedLoc(Context.getLocation(ID, Line, Column));
+ return DecomposedLocation.second;
+ }
+
+ const std::string FileName = "fix.cpp";
+ FormatStyle Style = getLLVMStyle();
};
TEST_F(CleanUpReplacementsTest, FixOnlyAffectedCodeAfterReplacements) {
@@ -268,17 +294,247 @@ TEST_F(CleanUpReplacementsTest, FixOnlyAffectedCodeAfterReplacements) {
"namespace D { int i; }\n\n"
"int x= 0;"
"}";
- FileID ID = Context.createInMemoryFile("fix.cpp", Code);
- tooling::Replacements Replaces;
- Replaces.insert(tooling::Replacement(Context.Sources,
- Context.getLocation(ID, 3, 3), 6, ""));
- Replaces.insert(tooling::Replacement(Context.Sources,
- Context.getLocation(ID, 9, 34), 6, ""));
-
- format::FormatStyle Style = format::getLLVMStyle();
- auto FinalReplaces = formatReplacements(
- Code, cleanupAroundReplacements(Code, Replaces, Style), Style);
- EXPECT_EQ(Expected, applyAllReplacements(Code, FinalReplaces));
+ tooling::Replacements Replaces = {
+ createReplacement(getOffset(Code, 3, 3), 6, ""),
+ createReplacement(getOffset(Code, 9, 34), 6, "")};
+
+ EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, NoExistingIncludeWithoutDefine) {
+ std::string Code = "int main() {}";
+ std::string Expected = "#include \"a.h\"\n"
+ "int main() {}";
+ tooling::Replacements Replaces = {createInsertion("#include \"a.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, NoExistingIncludeWithDefine) {
+ std::string Code = "#ifndef A_H\n"
+ "#define A_H\n"
+ "class A {};\n"
+ "#define MMM 123\n"
+ "#endif";
+ std::string Expected = "#ifndef A_H\n"
+ "#define A_H\n"
+ "#include \"b.h\"\n"
+ "class A {};\n"
+ "#define MMM 123\n"
+ "#endif";
+
+ tooling::Replacements Replaces = {createInsertion("#include \"b.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertBeforeCategoryWithLowerPriority) {
+ std::string Code = "#ifndef A_H\n"
+ "#define A_H\n"
+ "\n"
+ "\n"
+ "\n"
+ "#include <vector>\n"
+ "class A {};\n"
+ "#define MMM 123\n"
+ "#endif";
+ std::string Expected = "#ifndef A_H\n"
+ "#define A_H\n"
+ "\n"
+ "\n"
+ "\n"
+ "#include \"a.h\"\n"
+ "#include <vector>\n"
+ "class A {};\n"
+ "#define MMM 123\n"
+ "#endif";
+
+ tooling::Replacements Replaces = {createInsertion("#include \"a.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertAfterMainHeader) {
+ std::string Code = "#include \"fix.h\"\n"
+ "\n"
+ "int main() {}";
+ std::string Expected = "#include \"fix.h\"\n"
+ "#include <a>\n"
+ "\n"
+ "int main() {}";
+ tooling::Replacements Replaces = {createInsertion("#include <a>")};
+ Style = format::getGoogleStyle(format::FormatStyle::LanguageKind::LK_Cpp);
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertBeforeSystemHeaderLLVM) {
+ std::string Code = "#include <memory>\n"
+ "\n"
+ "int main() {}";
+ std::string Expected = "#include \"z.h\"\n"
+ "#include <memory>\n"
+ "\n"
+ "int main() {}";
+ tooling::Replacements Replaces = {createInsertion("#include \"z.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertAfterSystemHeaderGoogle) {
+ std::string Code = "#include <memory>\n"
+ "\n"
+ "int main() {}";
+ std::string Expected = "#include <memory>\n"
+ "#include \"z.h\"\n"
+ "\n"
+ "int main() {}";
+ tooling::Replacements Replaces = {createInsertion("#include \"z.h\"")};
+ Style = format::getGoogleStyle(format::FormatStyle::LanguageKind::LK_Cpp);
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertOneIncludeLLVMStyle) {
+ std::string Code = "#include \"x/fix.h\"\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"clang/Format/Format.h\"\n"
+ "#include <memory>\n";
+ std::string Expected = "#include \"x/fix.h\"\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"d.h\"\n"
+ "#include \"clang/Format/Format.h\"\n"
+ "#include \"llvm/x/y.h\"\n"
+ "#include <memory>\n";
+ tooling::Replacements Replaces = {createInsertion("#include \"d.h\""),
+ createInsertion("#include \"llvm/x/y.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertMultipleIncludesLLVMStyle) {
+ std::string Code = "#include \"x/fix.h\"\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"clang/Format/Format.h\"\n"
+ "#include <memory>\n";
+ std::string Expected = "#include \"x/fix.h\"\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"new/new.h\"\n"
+ "#include \"clang/Format/Format.h\"\n"
+ "#include <memory>\n"
+ "#include <list>\n";
+ tooling::Replacements Replaces = {createInsertion("#include <list>"),
+ createInsertion("#include \"new/new.h\"")};
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertNewSystemIncludeGoogleStyle) {
+ std::string Code = "#include \"x/fix.h\"\n"
+ "\n"
+ "#include \"y/a.h\"\n"
+ "#include \"z/b.h\"\n";
+ // FIXME: inserting after the empty line following the main header might be
+ // prefered.
+ std::string Expected = "#include \"x/fix.h\"\n"
+ "#include <vector>\n"
+ "\n"
+ "#include \"y/a.h\"\n"
+ "#include \"z/b.h\"\n";
+ tooling::Replacements Replaces = {createInsertion("#include <vector>")};
+ Style = format::getGoogleStyle(format::FormatStyle::LanguageKind::LK_Cpp);
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertMultipleIncludesGoogleStyle) {
+ std::string Code = "#include \"x/fix.h\"\n"
+ "\n"
+ "#include <vector>\n"
+ "\n"
+ "#include \"y/a.h\"\n"
+ "#include \"z/b.h\"\n";
+ std::string Expected = "#include \"x/fix.h\"\n"
+ "\n"
+ "#include <vector>\n"
+ "#include <list>\n"
+ "\n"
+ "#include \"y/a.h\"\n"
+ "#include \"z/b.h\"\n"
+ "#include \"x/x.h\"\n";
+ tooling::Replacements Replaces = {createInsertion("#include <list>"),
+ createInsertion("#include \"x/x.h\"")};
+ Style = format::getGoogleStyle(format::FormatStyle::LanguageKind::LK_Cpp);
+ EXPECT_EQ(Expected, apply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertMultipleNewHeadersAndSortLLVM) {
+ std::string Code = "\nint x;";
+ std::string Expected = "#include \"fix.h\"\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"c.h\"\n"
+ "#include <list>\n"
+ "#include <vector>\n"
+ "\nint x;";
+ tooling::Replacements Replaces = {createInsertion("#include \"a.h\""),
+ createInsertion("#include \"c.h\""),
+ createInsertion("#include \"b.h\""),
+ createInsertion("#include <vector>"),
+ createInsertion("#include <list>"),
+ createInsertion("#include \"fix.h\"")};
+ EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, InsertMultipleNewHeadersAndSortGoogle) {
+ std::string Code = "\nint x;";
+ std::string Expected = "#include \"fix.h\"\n"
+ "#include <list>\n"
+ "#include <vector>\n"
+ "#include \"a.h\"\n"
+ "#include \"b.h\"\n"
+ "#include \"c.h\"\n"
+ "\nint x;";
+ tooling::Replacements Replaces = {createInsertion("#include \"a.h\""),
+ createInsertion("#include \"c.h\""),
+ createInsertion("#include \"b.h\""),
+ createInsertion("#include <vector>"),
+ createInsertion("#include <list>"),
+ createInsertion("#include \"fix.h\"")};
+ Style = format::getGoogleStyle(format::FormatStyle::LanguageKind::LK_Cpp);
+ EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, FormatCorrectLineWhenHeadersAreInserted) {
+ std::string Code = "\n"
+ "int a;\n"
+ "int a;\n"
+ "int a;";
+
+ std::string Expected = "#include \"x.h\"\n"
+ "#include \"y.h\"\n"
+ "#include \"clang/x/x.h\"\n"
+ "#include <list>\n"
+ "#include <vector>\n"
+ "\n"
+ "int a;\n"
+ "int b;\n"
+ "int a;";
+ tooling::Replacements Replaces = {
+ createReplacement(getOffset(Code, 3, 8), 1, "b"),
+ createInsertion("#include <vector>"),
+ createInsertion("#include <list>"),
+ createInsertion("#include \"clang/x/x.h\""),
+ createInsertion("#include \"y.h\""),
+ createInsertion("#include \"x.h\"")};
+ EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
+}
+
+TEST_F(CleanUpReplacementsTest, NotConfusedByDefine) {
+ std::string Code = "void f() {}\n"
+ "#define A \\\n"
+ " int i;";
+ std::string Expected = "#include <vector>\n"
+ "void f() {}\n"
+ "#define A \\\n"
+ " int i;";
+ tooling::Replacements Replaces = {createInsertion("#include <vector>")};
+ EXPECT_EQ(Expected, formatAndApply(Code, Replaces));
}
} // end namespace
OpenPOWER on IntegriCloud