|  | //===- unittest/Format/FormatTestSelective.cpp - Formatting unit tests ----===// | 
|  | // | 
|  | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | 
|  | // See https://llvm.org/LICENSE.txt for license information. | 
|  | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | 
|  | // | 
|  | //===----------------------------------------------------------------------===// | 
|  |  | 
|  | #include "FormatTestUtils.h" | 
|  | #include "clang/Format/Format.h" | 
|  | #include "llvm/Support/Debug.h" | 
|  | #include "gtest/gtest.h" | 
|  |  | 
|  | #define DEBUG_TYPE "format-test" | 
|  |  | 
|  | namespace clang { | 
|  | namespace format { | 
|  | namespace { | 
|  |  | 
|  | class FormatTestSelective : public testing::Test { | 
|  | protected: | 
|  | std::string format(StringRef Code, unsigned Offset, unsigned Length) { | 
|  | LLVM_DEBUG(llvm::errs() << "---\n"); | 
|  | LLVM_DEBUG(llvm::errs() << Code << "\n\n"); | 
|  | std::vector<tooling::Range> Ranges(1, tooling::Range(Offset, Length)); | 
|  | FormattingAttemptStatus Status; | 
|  | tooling::Replacements Replaces = | 
|  | reformat(Style, Code, Ranges, "<stdin>", &Status); | 
|  | EXPECT_TRUE(Status.FormatComplete) << Code << "\n\n"; | 
|  | auto Result = applyAllReplacements(Code, Replaces); | 
|  | EXPECT_TRUE(static_cast<bool>(Result)); | 
|  | LLVM_DEBUG(llvm::errs() << "\n" << *Result << "\n\n"); | 
|  | return *Result; | 
|  | } | 
|  |  | 
|  | FormatStyle Style = getLLVMStyle(); | 
|  | }; | 
|  |  | 
|  | TEST_F(FormatTestSelective, RemovesTrailingWhitespaceOfFormattedLine) { | 
|  | EXPECT_EQ("int a;\nint b;", format("int a; \nint b;", 0, 0)); | 
|  | EXPECT_EQ("int a;", format("int a;         ", 0, 0)); | 
|  | EXPECT_EQ("int a;\n", format("int a;  \n   \n   \n ", 0, 0)); | 
|  | EXPECT_EQ("int a;\nint b;    ", format("int a;  \nint b;    ", 0, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, FormatsCorrectRegionForLeadingWhitespace) { | 
|  | EXPECT_EQ("{int b;\n" | 
|  | "  int a;\n" | 
|  | "}", | 
|  | format("{int b;\n  int  a;}", 8, 0)); | 
|  | EXPECT_EQ("{\n" | 
|  | "  int b;\n" | 
|  | "  int  a;}", | 
|  | format("{int b;\n  int  a;}", 7, 0)); | 
|  |  | 
|  | Style.ColumnLimit = 12; | 
|  | EXPECT_EQ("#define A  \\\n" | 
|  | "  int a;   \\\n" | 
|  | "  int b;", | 
|  | format("#define A  \\\n" | 
|  | "  int a;   \\\n" | 
|  | "    int b;", | 
|  | 26, 0)); | 
|  | EXPECT_EQ("#define A  \\\n" | 
|  | "  int a;   \\\n" | 
|  | "  int b;", | 
|  | format("#define A  \\\n" | 
|  | "  int a;   \\\n" | 
|  | "  int b;", | 
|  | 25, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, FormatLineWhenInvokedOnTrailingNewline) { | 
|  | EXPECT_EQ("int  b;\n\nint a;", format("int  b;\n\nint a;", 8, 0)); | 
|  | EXPECT_EQ("int b;\n\nint a;", format("int  b;\n\nint a;", 7, 0)); | 
|  |  | 
|  | // This might not strictly be correct, but is likely good in all practical | 
|  | // cases. | 
|  | EXPECT_EQ("int b;\nint a;", format("int  b;int a;", 7, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, RemovesWhitespaceWhenTriggeredOnEmptyLine) { | 
|  | EXPECT_EQ("int  a;\n\n int b;", format("int  a;\n  \n\n int b;", 8, 0)); | 
|  | EXPECT_EQ("int  a;\n\n int b;", format("int  a;\n  \n\n int b;", 9, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, ReformatsMovedLines) { | 
|  | EXPECT_EQ( | 
|  | "template <typename T> T *getFETokenInfo() const {\n" | 
|  | "  return static_cast<T *>(FETokenInfo);\n" | 
|  | "}\n" | 
|  | "int  a; // <- Should not be formatted", | 
|  | format( | 
|  | "template<typename T>\n" | 
|  | "T *getFETokenInfo() const { return static_cast<T*>(FETokenInfo); }\n" | 
|  | "int  a; // <- Should not be formatted", | 
|  | 9, 5)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, FormatsIfWithoutCompoundStatement) { | 
|  | Style.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_WithoutElse; | 
|  | EXPECT_EQ("if (a) return;", format("if(a)\nreturn;", 7, 1)); | 
|  | EXPECT_EQ("if (a) return; // comment", | 
|  | format("if(a)\nreturn; // comment", 20, 1)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, FormatsCommentsLocally) { | 
|  | EXPECT_EQ("int a;    // comment\n" | 
|  | "int    b; // comment", | 
|  | format("int   a; // comment\n" | 
|  | "int    b; // comment", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("int a; // comment\n" | 
|  | "       // line 2\n" | 
|  | "int b;", | 
|  | format("int   a; // comment\n" | 
|  | "            // line 2\n" | 
|  | "int b;", | 
|  | 28, 0)); | 
|  | EXPECT_EQ("int   a; // comment\n" | 
|  | "// comment 2\n" | 
|  | "int b;", | 
|  | format("int   a; // comment\n" | 
|  | "// comment 2\n" | 
|  | "int b;", | 
|  | 28, 0)); | 
|  | EXPECT_EQ("int aaaaaa; // comment\n" | 
|  | "int b;\n" | 
|  | "int c; // unrelated comment", | 
|  | format("int aaaaaa; // comment\n" | 
|  | "int b;\n" | 
|  | "int   c; // unrelated comment", | 
|  | 31, 0)); | 
|  |  | 
|  | EXPECT_EQ("int a; // This\n" | 
|  | "       // is\n" | 
|  | "       // a", | 
|  | format("int a;      // This\n" | 
|  | "            // is\n" | 
|  | "            // a", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("int a; // This\n" | 
|  | "       // is\n" | 
|  | "       // a\n" | 
|  | "// This is b\n" | 
|  | "int b;", | 
|  | format("int a; // This\n" | 
|  | "     // is\n" | 
|  | "     // a\n" | 
|  | "// This is b\n" | 
|  | "int b;", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("int a; // This\n" | 
|  | "       // is\n" | 
|  | "       // a\n" | 
|  | "\n" | 
|  | "//This is unrelated", | 
|  | format("int a; // This\n" | 
|  | "     // is\n" | 
|  | "     // a\n" | 
|  | "\n" | 
|  | "//This is unrelated", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("int a;\n" | 
|  | "// This is\n" | 
|  | "// not formatted.   ", | 
|  | format("int a;\n" | 
|  | "// This is\n" | 
|  | "// not formatted.   ", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("int x;  // Format this line.\n" | 
|  | "int xx; //\n" | 
|  | "int xxxxx; //", | 
|  | format("int x; // Format this line.\n" | 
|  | "int xx; //\n" | 
|  | "int xxxxx; //", | 
|  | 0, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, ContinueReindenting) { | 
|  | // When we change an indent, we continue formatting as long as following | 
|  | // lines are not indented correctly. | 
|  | EXPECT_EQ("int   i;\n" | 
|  | "int b;\n" | 
|  | "int c;\n" | 
|  | "int d;\n" | 
|  | "int e;\n" | 
|  | "  int f;", | 
|  | format("int   i;\n" | 
|  | "  int b;\n" | 
|  | " int   c;\n" | 
|  | "  int d;\n" | 
|  | "int e;\n" | 
|  | "  int f;", | 
|  | 11, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, ReindentClosingBrace) { | 
|  | EXPECT_EQ("int   i;\n" | 
|  | "int f() {\n" | 
|  | "  int a;\n" | 
|  | "  int b;\n" | 
|  | "}\n" | 
|  | " int c;", | 
|  | format("int   i;\n" | 
|  | "  int f(){\n" | 
|  | "int a;\n" | 
|  | "int b;\n" | 
|  | "  }\n" | 
|  | " int c;", | 
|  | 11, 0)); | 
|  | EXPECT_EQ("void f() {\n" | 
|  | "  if (foo) {\n" | 
|  | "    b();\n" | 
|  | "  } else {\n" | 
|  | "    c();\n" | 
|  | "  }\n" | 
|  | "int d;\n" | 
|  | "}", | 
|  | format("void f() {\n" | 
|  | "  if (foo) {\n" | 
|  | "b();\n" | 
|  | "}else{\n" | 
|  | "c();\n" | 
|  | "}\n" | 
|  | "int d;\n" | 
|  | "}", | 
|  | 13, 0)); | 
|  | EXPECT_EQ("int i = []() {\n" | 
|  | "  class C {\n" | 
|  | "    int a;\n" | 
|  | "    int b;\n" | 
|  | "  };\n" | 
|  | "  int c;\n" | 
|  | "};", | 
|  | format("int i = []() {\n" | 
|  | "  class C{\n" | 
|  | "int a;\n" | 
|  | "int b;\n" | 
|  | "};\n" | 
|  | "int c;\n" | 
|  | "  };", | 
|  | 17, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, IndividualStatementsOfNestedBlocks) { | 
|  | EXPECT_EQ("DEBUG({\n" | 
|  | "  int i;\n" | 
|  | "  int        j;\n" | 
|  | "});", | 
|  | format("DEBUG(   {\n" | 
|  | "  int        i;\n" | 
|  | "  int        j;\n" | 
|  | "}   )  ;", | 
|  | 20, 1)); | 
|  | EXPECT_EQ("DEBUG(   {\n" | 
|  | "  int        i;\n" | 
|  | "  int j;\n" | 
|  | "}   )  ;", | 
|  | format("DEBUG(   {\n" | 
|  | "  int        i;\n" | 
|  | "  int        j;\n" | 
|  | "}   )  ;", | 
|  | 41, 1)); | 
|  | EXPECT_EQ("DEBUG(   {\n" | 
|  | "    int        i;\n" | 
|  | "    int j;\n" | 
|  | "}   )  ;", | 
|  | format("DEBUG(   {\n" | 
|  | "    int        i;\n" | 
|  | "    int        j;\n" | 
|  | "}   )  ;", | 
|  | 41, 1)); | 
|  | EXPECT_EQ("DEBUG({\n" | 
|  | "  int i;\n" | 
|  | "  int j;\n" | 
|  | "});", | 
|  | format("DEBUG(   {\n" | 
|  | "    int        i;\n" | 
|  | "    int        j;\n" | 
|  | "}   )  ;", | 
|  | 20, 1)); | 
|  |  | 
|  | EXPECT_EQ("Debug({\n" | 
|  | "        if (aaaaaaaaaaaaaaaaaaaaaaaa)\n" | 
|  | "          return;\n" | 
|  | "      },\n" | 
|  | "      a);", | 
|  | format("Debug({\n" | 
|  | "        if (aaaaaaaaaaaaaaaaaaaaaaaa)\n" | 
|  | "             return;\n" | 
|  | "      },\n" | 
|  | "      a);", | 
|  | 50, 1)); | 
|  | EXPECT_EQ("DEBUG({\n" | 
|  | "  DEBUG({\n" | 
|  | "    int a;\n" | 
|  | "    int b;\n" | 
|  | "  }) ;\n" | 
|  | "});", | 
|  | format("DEBUG({\n" | 
|  | "  DEBUG({\n" | 
|  | "    int a;\n" | 
|  | "    int    b;\n" // Format this line only. | 
|  | "  }) ;\n"        // Don't touch this line. | 
|  | "});", | 
|  | 35, 0)); | 
|  | EXPECT_EQ("DEBUG({\n" | 
|  | "  int a; //\n" | 
|  | "});", | 
|  | format("DEBUG({\n" | 
|  | "    int a; //\n" | 
|  | "});", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("someFunction(\n" | 
|  | "    [] {\n" | 
|  | "      // Only with this comment.\n" | 
|  | "      int i; // invoke formatting here.\n" | 
|  | "    }, // force line break\n" | 
|  | "    aaa);", | 
|  | format("someFunction(\n" | 
|  | "    [] {\n" | 
|  | "      // Only with this comment.\n" | 
|  | "      int   i; // invoke formatting here.\n" | 
|  | "    }, // force line break\n" | 
|  | "    aaa);", | 
|  | 63, 1)); | 
|  |  | 
|  | EXPECT_EQ("int longlongname; // comment\n" | 
|  | "int x = f({\n" | 
|  | "  int x; // comment\n" | 
|  | "  int y; // comment\n" | 
|  | "});", | 
|  | format("int longlongname; // comment\n" | 
|  | "int x = f({\n" | 
|  | "  int x; // comment\n" | 
|  | "  int y; // comment\n" | 
|  | "});", | 
|  | 65, 0)); | 
|  | EXPECT_EQ("int s = f({\n" | 
|  | "  class X {\n" | 
|  | "  public:\n" | 
|  | "    void f();\n" | 
|  | "  };\n" | 
|  | "});", | 
|  | format("int s = f({\n" | 
|  | "  class X {\n" | 
|  | "    public:\n" | 
|  | "    void f();\n" | 
|  | "  };\n" | 
|  | "});", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("SomeFunction(\n" | 
|  | "    [] {\n" | 
|  | "      int i;\n" | 
|  | "      return i;\n" // Format this line. | 
|  | "    },\n" | 
|  | "    [] {\n" | 
|  | "       return 2;\n" // Don't fix this. | 
|  | "    });", | 
|  | format("SomeFunction(\n" | 
|  | "    [] {\n" | 
|  | "      int i;\n" | 
|  | "       return i;\n" // Format this line. | 
|  | "    },\n" | 
|  | "    [] {\n" | 
|  | "       return 2;\n" // Don't fix this. | 
|  | "    });", | 
|  | 40, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, WrongIndent) { | 
|  | EXPECT_EQ("namespace {\n" | 
|  | "int i;\n" | 
|  | "int j;\n" | 
|  | "}", | 
|  | format("namespace {\n" | 
|  | "  int i;\n" // Format here. | 
|  | "  int j;\n" | 
|  | "}", | 
|  | 15, 0)); | 
|  | EXPECT_EQ("namespace {\n" | 
|  | "  int i;\n" | 
|  | "  int j;\n" | 
|  | "}", | 
|  | format("namespace {\n" | 
|  | "  int i;\n" | 
|  | "  int j;\n" // Format here. | 
|  | "}", | 
|  | 24, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, AlwaysFormatsEntireMacroDefinitions) { | 
|  | Style.AlignEscapedNewlines = FormatStyle::ENAS_Left; | 
|  | EXPECT_EQ("int  i;\n" | 
|  | "#define A \\\n" | 
|  | "  int i;  \\\n" | 
|  | "  int j\n" | 
|  | "int  k;", | 
|  | format("int  i;\n" | 
|  | "#define A  \\\n" | 
|  | " int   i    ;  \\\n" | 
|  | " int   j\n" | 
|  | "int  k;", | 
|  | 8, 0)); // 8: position of "#define". | 
|  | EXPECT_EQ("int  i;\n" | 
|  | "#define A \\\n" | 
|  | "  int i;  \\\n" | 
|  | "  int j\n" | 
|  | "int  k;", | 
|  | format("int  i;\n" | 
|  | "#define A  \\\n" | 
|  | " int   i    ;  \\\n" | 
|  | " int   j\n" | 
|  | "int  k;", | 
|  | 45, 0)); // 45: position of "j". | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, ReformatRegionAdjustsIndent) { | 
|  | EXPECT_EQ("{\n" | 
|  | "{\n" | 
|  | "a;\n" | 
|  | "b;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | format("{\n" | 
|  | "{\n" | 
|  | "a;\n" | 
|  | "     b;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | 13, 2)); | 
|  | EXPECT_EQ("{\n" | 
|  | "{\n" | 
|  | "  a;\n" | 
|  | "  b;\n" | 
|  | "  c;\n" | 
|  | " d;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | format("{\n" | 
|  | "{\n" | 
|  | "     a;\n" | 
|  | "   b;\n" | 
|  | "  c;\n" | 
|  | " d;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | 9, 2)); | 
|  | EXPECT_EQ("{\n" | 
|  | "{\n" | 
|  | "public:\n" | 
|  | "  b;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | format("{\n" | 
|  | "{\n" | 
|  | "public:\n" | 
|  | "     b;\n" | 
|  | "}\n" | 
|  | "}", | 
|  | 17, 2)); | 
|  | EXPECT_EQ("{\n" | 
|  | "{\n" | 
|  | "a;\n" | 
|  | "}\n" | 
|  | "{\n" | 
|  | "  b; //\n" | 
|  | "}\n" | 
|  | "}", | 
|  | format("{\n" | 
|  | "{\n" | 
|  | "a;\n" | 
|  | "}\n" | 
|  | "{\n" | 
|  | "           b; //\n" | 
|  | "}\n" | 
|  | "}", | 
|  | 22, 2)); | 
|  | EXPECT_EQ("  {\n" | 
|  | "    a; //\n" | 
|  | "  }", | 
|  | format("  {\n" | 
|  | "a; //\n" | 
|  | "  }", | 
|  | 4, 2)); | 
|  | EXPECT_EQ("void f() {}\n" | 
|  | "void g() {}", | 
|  | format("void f() {}\n" | 
|  | "void g() {}", | 
|  | 13, 0)); | 
|  | EXPECT_EQ("int a; // comment\n" | 
|  | "       // line 2\n" | 
|  | "int b;", | 
|  | format("int a; // comment\n" | 
|  | "       // line 2\n" | 
|  | "  int b;", | 
|  | 35, 0)); | 
|  |  | 
|  | EXPECT_EQ(" void f() {\n" | 
|  | "#define A 1\n" | 
|  | " }", | 
|  | format(" void f() {\n" | 
|  | "     #define A 1\n" // Format this line. | 
|  | " }", | 
|  | 20, 0)); | 
|  | EXPECT_EQ(" void f() {\n" | 
|  | "    int i;\n" | 
|  | "#define A \\\n" | 
|  | "    int i;  \\\n" | 
|  | "   int j;\n" | 
|  | "    int k;\n" | 
|  | " }", | 
|  | format(" void f() {\n" | 
|  | "    int i;\n" | 
|  | "#define A \\\n" | 
|  | "    int i;  \\\n" | 
|  | "   int j;\n" | 
|  | "      int k;\n" // Format this line. | 
|  | " }", | 
|  | 67, 0)); | 
|  |  | 
|  | Style.ColumnLimit = 11; | 
|  | EXPECT_EQ("  int a;\n" | 
|  | "  void\n" | 
|  | "  ffffff() {\n" | 
|  | "  }", | 
|  | format("  int a;\n" | 
|  | "void ffffff() {}", | 
|  | 11, 0)); | 
|  |  | 
|  | // https://github.com/llvm/llvm-project/issues/59178 | 
|  | Style = getMozillaStyle(); | 
|  | EXPECT_EQ("int a()\n" | 
|  | "{\n" | 
|  | "return 0;\n" | 
|  | "}\n" | 
|  | "int b()\n" | 
|  | "{\n" | 
|  | "  return 42;\n" | 
|  | "}", | 
|  | format("int a()\n" | 
|  | "{\n" | 
|  | "return 0;\n" | 
|  | "}\n" | 
|  | "int b()\n" | 
|  | "{\n" | 
|  | "return 42;\n" // Format this line only | 
|  | "}", | 
|  | 32, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, UnderstandsTabs) { | 
|  | Style.IndentWidth = 8; | 
|  | Style.UseTab = FormatStyle::UT_Always; | 
|  | Style.AlignEscapedNewlines = FormatStyle::ENAS_Left; | 
|  | EXPECT_EQ("void f() {\n" | 
|  | "\tf();\n" | 
|  | "\tg();\n" | 
|  | "}", | 
|  | format("void f() {\n" | 
|  | "\tf();\n" | 
|  | "\tg();\n" | 
|  | "}", | 
|  | 0, 0)); | 
|  | EXPECT_EQ("void f() {\n" | 
|  | "\tf();\n" | 
|  | "\tg();\n" | 
|  | "}", | 
|  | format("void f() {\n" | 
|  | "\tf();\n" | 
|  | "\tg();\n" | 
|  | "}", | 
|  | 16, 0)); | 
|  | EXPECT_EQ("void f() {\n" | 
|  | "  \tf();\n" | 
|  | "\tg();\n" | 
|  | "}", | 
|  | format("void f() {\n" | 
|  | "  \tf();\n" | 
|  | "  \tg();\n" | 
|  | "}", | 
|  | 21, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, StopFormattingWhenLeavingScope) { | 
|  | EXPECT_EQ( | 
|  | "void f() {\n" | 
|  | "  if (a) {\n" | 
|  | "    g();\n" | 
|  | "    h();\n" | 
|  | "  }\n" | 
|  | "\n" | 
|  | "void g() {\n" | 
|  | "}", | 
|  | format("void f() {\n" | 
|  | "  if (a) {\n" // Assume this was added without the closing brace. | 
|  | "  g();\n" | 
|  | "  h();\n" | 
|  | "}\n" | 
|  | "\n" | 
|  | "void g() {\n" // Make sure not to format this. | 
|  | "}", | 
|  | 15, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, SelectivelyRequoteJavaScript) { | 
|  | Style = getGoogleStyle(FormatStyle::LK_JavaScript); | 
|  | EXPECT_EQ("var x = \"a\";\n" | 
|  | "var x = 'a';\n" | 
|  | "var x = \"a\";", | 
|  | format("var x = \"a\";\n" | 
|  | "var x = \"a\";\n" | 
|  | "var x = \"a\";", | 
|  | 20, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, KeepsIndentAfterCommentSectionImport) { | 
|  | std::string Code = "#include <a> // line 1\n" // 23 chars long | 
|  | "             // line 2\n" // 23 chars long | 
|  | "\n"                       // this newline is char 47 | 
|  | "int i;";                  // this line is not indented | 
|  | EXPECT_EQ(Code, format(Code, 47, 1)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, DontAssert) { | 
|  | // https://llvm.org/PR53880 | 
|  | std::string Code = "void f() {\n" | 
|  | "  return a == 8 ? 32 : 16;\n" | 
|  | "}\n"; | 
|  | EXPECT_EQ(Code, format(Code, 40, 0)); | 
|  |  | 
|  | // https://llvm.org/PR56352 | 
|  | Style.CompactNamespaces = true; | 
|  | Style.NamespaceIndentation = FormatStyle::NI_All; | 
|  | Code = "\n" | 
|  | "namespace ns1 { namespace ns2 {\n" | 
|  | "}}"; | 
|  | EXPECT_EQ(Code, format(Code, 0, 0)); | 
|  |  | 
|  | // https://reviews.llvm.org/D151047#4369742 | 
|  | Style = getLLVMStyle(); | 
|  | Style.FixNamespaceComments = false; | 
|  | Code = "namespace ns {\n" | 
|  | "#define REF(alias) alias alias_var;\n" | 
|  | "}"; // Format this line only | 
|  | EXPECT_EQ(Code, format(Code, 51, 0)); | 
|  | } | 
|  |  | 
|  | TEST_F(FormatTestSelective, FormatMacroRegardlessOfPreviousIndent) { | 
|  | // clang-format currently does not (or should not) take into account the | 
|  | // indent of previous unformatted lines when formatting a PP directive. | 
|  | // Technically speaking, LevelIndentTracker::IndentForLevel is only for non-PP | 
|  | // lines. So these tests here check that the indent of previous non-PP lines | 
|  | // do not affect the formatting. If this requirement changes, the tests here | 
|  | // need to be adapted. | 
|  | Style = getLLVMStyle(); | 
|  |  | 
|  | const StringRef Code{"      class Foo {\n" | 
|  | "            void test() {\n" | 
|  | "    #ifdef 1\n" | 
|  | "                #define some\n" // format this line | 
|  | "         #endif\n" | 
|  | "    }};"}; | 
|  |  | 
|  | EXPECT_EQ(Style.IndentPPDirectives, | 
|  | FormatStyle::PPDirectiveIndentStyle::PPDIS_None); | 
|  | EXPECT_EQ("      class Foo {\n" | 
|  | "            void test() {\n" | 
|  | "    #ifdef 1\n" | 
|  | "#define some\n" // Formatted line | 
|  | "#endif\n"       // That this line is also formatted might be a bug. | 
|  | "            }};", // Ditto: Bug? | 
|  | format(Code, 57, 0)); | 
|  |  | 
|  | Style.IndentPPDirectives = | 
|  | FormatStyle::PPDirectiveIndentStyle::PPDIS_BeforeHash; | 
|  | EXPECT_EQ("      class Foo {\n" | 
|  | "            void test() {\n" | 
|  | "    #ifdef 1\n" | 
|  | "  #define some\n" // Formatted line | 
|  | "         #endif\n" | 
|  | "    }};", | 
|  | format(Code, 57, 0)); | 
|  |  | 
|  | Style.IndentPPDirectives = | 
|  | FormatStyle::PPDirectiveIndentStyle::PPDIS_AfterHash; | 
|  | EXPECT_EQ("      class Foo {\n" | 
|  | "            void test() {\n" | 
|  | "    #ifdef 1\n" | 
|  | "#  define some\n" // Formatted line | 
|  | "#endif\n" // That this line is also formatted might be a bug. | 
|  | "    }};", | 
|  | format(Code, 57, 0)); | 
|  | } | 
|  |  | 
|  | } // end namespace | 
|  | } // end namespace format | 
|  | } // end namespace clang |