]> granicus.if.org Git - clang/commitdiff
clang-format: Add option to allow short blocks on a single line.
authorDaniel Jasper <djasper@google.com>
Wed, 14 May 2014 09:33:35 +0000 (09:33 +0000)
committerDaniel Jasper <djasper@google.com>
Wed, 14 May 2014 09:33:35 +0000 (09:33 +0000)
With AllowShortBlocksOnASingleLine, clang-format allows:
  if (a) { return; }

Based on patch by Gonzalo BG, thank you!

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@208765 91177308-0d34-0410-b5e6-96231b3b80d8

docs/ClangFormatStyleOptions.rst
include/clang/Format/Format.h
lib/Format/Format.cpp
unittests/Format/FormatTest.cpp

index 27d5e7426adb47c79ce94038d5bf4ee6f46b67de..b2157dd832050a0d4fcdd6db2e9412f5de8f3394 100644 (file)
@@ -106,6 +106,11 @@ the configuration (without a prefix: ``Auto``).
   Allow putting all parameters of a function declaration onto
   the next line even if ``BinPackParameters`` is ``false``.
 
+**AllowShortBlocksOnASingleLine** (``bool``)
+  Allows contracting simple braced statements to a single line.
+
+  E.g., this allows ``if (a) { return; }`` to be put on a single line.
+
 **AllowShortFunctionsOnASingleLine** (``ShortFunctionStyle``)
   Dependent on the value, ``int f() { return 0; }`` can be put
   on a single line.
@@ -284,7 +289,7 @@ the configuration (without a prefix: ``Auto``).
 
 **ObjCSpaceAfterProperty** (``bool``)
   Add a space after ``@property`` in Objective-C, i.e. use
-  ``@property (readonly)`` instead of ``@property(readonly)``.
+  ``\@property (readonly)`` instead of ``\@property(readonly)``.
 
 **ObjCSpaceBeforeProtocolList** (``bool``)
   Add a space in front of an Objective-C protocol list, i.e. use
@@ -338,7 +343,7 @@ the configuration (without a prefix: ``Auto``).
 **SpacesBeforeTrailingComments** (``unsigned``)
   The number of spaces before trailing line comments (//-comments).
 
-  This does not affect trailing block comments (/\*\*/-comments) as those
+  This does not affect trailing block comments (/**/-comments) as those
   commonly have different usage patterns and a number of special cases.
 
 **SpacesInAngles** (``bool``)
index 09c37d1cf71911417b40dc1a0c32791e4d3f0e56..4356ff0b03938bec9d65160ba833dfce5a90bd15 100644 (file)
@@ -158,6 +158,11 @@ struct FormatStyle {
   /// the commas with the colon.
   bool BreakConstructorInitializersBeforeComma;
 
+  /// \brief Allows contracting simple braced statements to a single line.
+  ///
+  /// E.g., this allows <tt>if (a) { return; }</tt> to be put on a single line.
+  bool AllowShortBlocksOnASingleLine;
+
   /// \brief If \c true, <tt>if (a) return;</tt> can be put on a single
   /// line.
   bool AllowShortIfStatementsOnASingleLine;
@@ -338,6 +343,7 @@ struct FormatStyle {
                R.AllowAllParametersOfDeclarationOnNextLine &&
            AllowShortFunctionsOnASingleLine ==
                R.AllowShortFunctionsOnASingleLine &&
+           AllowShortBlocksOnASingleLine == R.AllowShortBlocksOnASingleLine &&
            AllowShortIfStatementsOnASingleLine ==
                R.AllowShortIfStatementsOnASingleLine &&
            AllowShortLoopsOnASingleLine == R.AllowShortLoopsOnASingleLine &&
index 60706b1b3bef6e1cb8084f6d07c075c96f97760e..e0b2961af3511a2f71e7777e4f8005da13cd2c3f 100644 (file)
@@ -151,6 +151,8 @@ template <> struct MappingTraits<FormatStyle> {
     IO.mapOptional("AlignTrailingComments", Style.AlignTrailingComments);
     IO.mapOptional("AllowAllParametersOfDeclarationOnNextLine",
                    Style.AllowAllParametersOfDeclarationOnNextLine);
+    IO.mapOptional("AllowShortBlocksOnASingleLine",
+                   Style.AllowShortBlocksOnASingleLine);
     IO.mapOptional("AllowShortIfStatementsOnASingleLine",
                    Style.AllowShortIfStatementsOnASingleLine);
     IO.mapOptional("AllowShortLoopsOnASingleLine",
@@ -263,6 +265,7 @@ FormatStyle getLLVMStyle() {
   LLVMStyle.AlignTrailingComments = true;
   LLVMStyle.AllowAllParametersOfDeclarationOnNextLine = true;
   LLVMStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_All;
+  LLVMStyle.AllowShortBlocksOnASingleLine = false;
   LLVMStyle.AllowShortIfStatementsOnASingleLine = false;
   LLVMStyle.AllowShortLoopsOnASingleLine = false;
   LLVMStyle.AlwaysBreakBeforeMultilineStrings = false;
@@ -609,7 +612,7 @@ private:
       return 0;
     if ((Style.BreakBeforeBraces == FormatStyle::BS_Allman ||
          Style.BreakBeforeBraces == FormatStyle::BS_GNU) &&
-        I[1]->First->is(tok::l_brace))
+        (I[1]->First->is(tok::l_brace) && !Style.AllowShortBlocksOnASingleLine))
       return 0;
     if (I[1]->InPPDirective != (*I)->InPPDirective ||
         (I[1]->InPPDirective && I[1]->First->HasUnescapedNewline))
@@ -635,16 +638,31 @@ private:
   tryMergeSimpleBlock(SmallVectorImpl<AnnotatedLine *>::const_iterator I,
                       SmallVectorImpl<AnnotatedLine *>::const_iterator E,
                       unsigned Limit) {
-    // First, check that the current line allows merging. This is the case if
-    // we're not in a control flow statement and the last token is an opening
-    // brace.
     AnnotatedLine &Line = **I;
-    if (Line.First->isOneOf(tok::kw_if, tok::kw_while, tok::kw_do, tok::r_brace,
-                            tok::kw_else, tok::kw_try, tok::kw_catch,
-                            tok::kw_for, tok::kw_case,
-                            // This gets rid of all ObjC @ keywords and methods.
-                            tok::at, tok::minus, tok::plus))
+
+    // Don't merge ObjC @ keywords and methods.
+    if (Line.First->isOneOf(tok::at, tok::minus, tok::plus))
+      return 0;
+
+    // Check that the current line allows merging. This depends on whether we
+    // are in a control flow statements as well as several style flags.
+    if (Line.First->isOneOf(tok::kw_else, tok::kw_case))
       return 0;
+    if (Line.First->isOneOf(tok::kw_if, tok::kw_while, tok::kw_do, tok::kw_try,
+                            tok::kw_catch, tok::kw_for, tok::r_brace)) {
+      if (!Style.AllowShortBlocksOnASingleLine)
+        return 0;
+      if (!Style.AllowShortIfStatementsOnASingleLine &&
+          Line.First->is(tok::kw_if))
+        return 0;
+      if (!Style.AllowShortLoopsOnASingleLine &&
+          Line.First->isOneOf(tok::kw_while, tok::kw_do, tok::kw_for))
+        return 0;
+      // FIXME: Consider an option to allow short exception handling clauses on
+      // a single line.
+      if (Line.First->isOneOf(tok::kw_try, tok::kw_catch))
+        return 0;
+    }
 
     FormatToken *Tok = I[1]->First;
     if (Tok->is(tok::r_brace) && !Tok->MustBreakBefore &&
@@ -672,7 +690,8 @@ private:
       if (I[1]->Last->Type == TT_LineComment)
         return 0;
       do {
-        if (Tok->isOneOf(tok::l_brace, tok::r_brace))
+        if (Tok->isOneOf(tok::l_brace, tok::r_brace) &&
+            !Style.AllowShortBlocksOnASingleLine)
           return 0;
         Tok = Tok->Next;
       } while (Tok);
index 93a0064e7dab617eb636d34e1018fd6fbc09b52f..7ac6cb49873eb12666ce047d79f5ef65ece63b55 100644 (file)
@@ -355,6 +355,46 @@ TEST_F(FormatTest, FormatLoopsWithoutCompoundStatement) {
                AllowsMergedLoops);
 }
 
+TEST_F(FormatTest, FormatShortBracedStatements) {
+  FormatStyle AllowSimpleBracedStatements = getLLVMStyle();
+  AllowSimpleBracedStatements.AllowShortBlocksOnASingleLine = true;
+
+  AllowSimpleBracedStatements.AllowShortIfStatementsOnASingleLine = true;
+  AllowSimpleBracedStatements.AllowShortLoopsOnASingleLine = true;
+
+  verifyFormat("if (true) {}", AllowSimpleBracedStatements);
+  verifyFormat("while (true) {}", AllowSimpleBracedStatements);
+  verifyFormat("for (;;) {}", AllowSimpleBracedStatements);
+  verifyFormat("if (true) { f(); }", AllowSimpleBracedStatements);
+  verifyFormat("while (true) { f(); }", AllowSimpleBracedStatements);
+  verifyFormat("for (;;) { f(); }", AllowSimpleBracedStatements);
+  verifyFormat("if (true) { //\n"
+               "  f();\n"
+               "}",
+               AllowSimpleBracedStatements);
+  verifyFormat("if (true) {\n"
+               "  f();\n"
+               "  f();\n"
+               "}",
+               AllowSimpleBracedStatements);
+
+  AllowSimpleBracedStatements.AllowShortIfStatementsOnASingleLine = false;
+  verifyFormat("if (true) {\n"
+               "  f();\n"
+               "}",
+               AllowSimpleBracedStatements);
+
+  AllowSimpleBracedStatements.AllowShortLoopsOnASingleLine = false;
+  verifyFormat("while (true) {\n"
+               "  f();\n"
+               "}",
+               AllowSimpleBracedStatements);
+  verifyFormat("for (;;) {\n"
+               "  f();\n"
+               "}",
+               AllowSimpleBracedStatements);
+}
+
 TEST_F(FormatTest, ParseIfElse) {
   verifyFormat("if (true)\n"
                "  if (true)\n"
@@ -7928,6 +7968,7 @@ TEST_F(FormatTest, ParsesConfiguration) {
   CHECK_PARSE_BOOL(AlignEscapedNewlinesLeft);
   CHECK_PARSE_BOOL(AlignTrailingComments);
   CHECK_PARSE_BOOL(AllowAllParametersOfDeclarationOnNextLine);
+  CHECK_PARSE_BOOL(AllowShortBlocksOnASingleLine);
   CHECK_PARSE_BOOL(AllowShortIfStatementsOnASingleLine);
   CHECK_PARSE_BOOL(AllowShortLoopsOnASingleLine);
   CHECK_PARSE_BOOL(AlwaysBreakTemplateDeclarations);