[clang] 6ef45b0 - [clang-format] Added new option IndentExternBlock
via cfe-commits
cfe-commits at lists.llvm.org
Wed May 20 13:30:51 PDT 2020
Author: mydeveloperday
Date: 2020-05-20T21:27:15+01:00
New Revision: 6ef45b0426a8c7b9764e102fb1a49561a3a2c118
URL: https://github.com/llvm/llvm-project/commit/6ef45b0426a8c7b9764e102fb1a49561a3a2c118
DIFF: https://github.com/llvm/llvm-project/commit/6ef45b0426a8c7b9764e102fb1a49561a3a2c118.diff
LOG: [clang-format] Added new option IndentExternBlock
Reviewers: MyDeveloperDay, krasimir, klimek, mitchell-stellar, Abpostelnicu
Patch By: MarcusJohnson91
Reviewed By: MyDeveloperDay, Abpostelnicu
Subscribers: sylvestre.ledru, Abpostelnicu, cfe-commits
Tags: #clang, #clang-format, #clang-tools-extra
Differential Revision: https://reviews.llvm.org/D75791
Added:
Modified:
clang/docs/ClangFormatStyleOptions.rst
clang/docs/ReleaseNotes.rst
clang/include/clang/Format/Format.h
clang/lib/Format/Format.cpp
clang/lib/Format/UnwrappedLineParser.cpp
clang/unittests/Format/FormatTest.cpp
Removed:
################################################################################
diff --git a/clang/docs/ClangFormatStyleOptions.rst b/clang/docs/ClangFormatStyleOptions.rst
index e5a5fd154849..2afa17973454 100644
--- a/clang/docs/ClangFormatStyleOptions.rst
+++ b/clang/docs/ClangFormatStyleOptions.rst
@@ -1739,6 +1739,52 @@ the configuration (without a prefix: ``Auto``).
plop(); plop();
} }
+**IndentExternBlock** (``IndentExternBlockStyle``)
+ IndentExternBlockStyle is the type of indenting of extern blocks.
+
+ Possible values:
+
+ * ``IEBS_AfterExternBlock`` (in configuration: ``AfterExternBlock``)
+ Backwards compatible with AfterExternBlock's indenting.
+
+ .. code-block:: c++
+
+ IndentExternBlock: AfterExternBlock
+ BraceWrapping.AfterExternBlock: true
+ extern "C"
+ {
+ void foo();
+ }
+
+
+ .. code-block:: c++
+
+ IndentExternBlock: AfterExternBlock
+ BraceWrapping.AfterExternBlock: false
+ extern "C" {
+ void foo();
+ }
+
+ * ``IEBS_NoIndent`` (in configuration: ``NoIndent``)
+ Does not indent extern blocks.
+
+ .. code-block:: c++
+
+ extern "C" {
+ void foo();
+ }
+
+ * ``IEBS_Indent`` (in configuration: ``Indent``)
+ Indents extern blocks.
+
+ .. code-block:: c++
+
+ extern "C" {
+ void foo();
+ }
+
+
+
**IndentGotoLabels** (``bool``)
Indent goto labels.
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 48c1c9ea019d..16f5915856fd 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -251,6 +251,23 @@ AST Matchers
clang-format
------------
+- Option ``IndentExternBlock`` has been added to optionally apply indenting inside ``extern "C"`` and ``extern "C++"`` blocks.
+
+- ``IndentExternBlock`` option accepts ``AfterExternBlock`` to use the old behavior, as well as Indent and NoIndent options, which map to true and false, respectively.
+
+ .. code-block:: c++
+
+ Indent: NoIndent:
+ #ifdef __cplusplus #ifdef __cplusplus
+ extern "C" { extern "C++" {
+ #endif #endif
+
+ void f(void); void f(void);
+
+ #ifdef __cplusplus #ifdef __cplusplus
+ } }
+ #endif #endif
+
- Option ``IndentCaseBlocks`` has been added to support treating the block
following a switch case label as a scope block which gets indented itself.
It helps avoid having the closing bracket align with the switch statement's
@@ -316,7 +333,7 @@ clang-format
before the ```while`` in a do..while loop. By default the value is (``false``)
In previous releases ``IndentBraces`` implied ``BraceWrapping.BeforeWhile``.
- If using a Custom BraceWrapping style you may need to now set
+ If using a Custom BraceWrapping style you may need to now set
``BraceWrapping.BeforeWhile`` to (``true``) to be explicit.
.. code-block:: c++
@@ -332,7 +349,6 @@ clang-format
foo();
} while(1);
-
libclang
--------
diff --git a/clang/include/clang/Format/Format.h b/clang/include/clang/Format/Format.h
index 05a9cd2d418d..96b73211d9ff 100755
--- a/clang/include/clang/Format/Format.h
+++ b/clang/include/clang/Format/Format.h
@@ -1028,7 +1028,7 @@ struct FormatStyle {
/// int foo();
/// }
/// \endcode
- bool AfterExternBlock;
+ bool AfterExternBlock; // Partially superseded by IndentExternBlock
/// Wrap before ``catch``.
/// \code
/// true:
@@ -1517,6 +1517,45 @@ struct FormatStyle {
/// The preprocessor directive indenting style to use.
PPDirectiveIndentStyle IndentPPDirectives;
+ /// Indents extern blocks
+ enum IndentExternBlockStyle {
+ /// Backwards compatible with AfterExternBlock's indenting.
+ /// \code
+ /// IndentExternBlock: AfterExternBlock
+ /// BraceWrapping.AfterExternBlock: true
+ /// extern "C"
+ /// {
+ /// void foo();
+ /// }
+ /// \endcode
+ ///
+ /// \code
+ /// IndentExternBlock: AfterExternBlock
+ /// BraceWrapping.AfterExternBlock: false
+ /// extern "C" {
+ /// void foo();
+ /// }
+ /// \endcode
+ IEBS_AfterExternBlock,
+ /// Does not indent extern blocks.
+ /// \code
+ /// extern "C" {
+ /// void foo();
+ /// }
+ /// \endcode
+ IEBS_NoIndent,
+ /// Indents extern blocks.
+ /// \code
+ /// extern "C" {
+ /// void foo();
+ /// }
+ /// \endcode
+ IEBS_Indent,
+ };
+
+ /// IndentExternBlockStyle is the type of indenting of extern blocks.
+ IndentExternBlockStyle IndentExternBlock;
+
/// The number of columns to use for indentation.
/// \code
/// IndentWidth: 3
@@ -2302,6 +2341,7 @@ struct FormatStyle {
IndentCaseBlocks == R.IndentCaseBlocks &&
IndentGotoLabels == R.IndentGotoLabels &&
IndentPPDirectives == R.IndentPPDirectives &&
+ IndentExternBlock == R.IndentExternBlock &&
IndentWidth == R.IndentWidth && Language == R.Language &&
IndentWrappedFunctionNames == R.IndentWrappedFunctionNames &&
JavaImportGroups == R.JavaImportGroups &&
diff --git a/clang/lib/Format/Format.cpp b/clang/lib/Format/Format.cpp
index 79e9f35de707..f3743921d52e 100644
--- a/clang/lib/Format/Format.cpp
+++ b/clang/lib/Format/Format.cpp
@@ -234,6 +234,17 @@ struct ScalarEnumerationTraits<FormatStyle::PPDirectiveIndentStyle> {
}
};
+template <>
+struct ScalarEnumerationTraits<FormatStyle::IndentExternBlockStyle> {
+ static void enumeration(IO &IO, FormatStyle::IndentExternBlockStyle &Value) {
+ IO.enumCase(Value, "AfterExternBlock", FormatStyle::IEBS_AfterExternBlock);
+ IO.enumCase(Value, "Indent", FormatStyle::IEBS_Indent);
+ IO.enumCase(Value, "NoIndent", FormatStyle::IEBS_NoIndent);
+ IO.enumCase(Value, "true", FormatStyle::IEBS_Indent);
+ IO.enumCase(Value, "false", FormatStyle::IEBS_NoIndent);
+ }
+};
+
template <>
struct ScalarEnumerationTraits<FormatStyle::ReturnTypeBreakingStyle> {
static void enumeration(IO &IO, FormatStyle::ReturnTypeBreakingStyle &Value) {
@@ -512,6 +523,7 @@ template <> struct MappingTraits<FormatStyle> {
IO.mapOptional("IndentCaseBlocks", Style.IndentCaseBlocks);
IO.mapOptional("IndentGotoLabels", Style.IndentGotoLabels);
IO.mapOptional("IndentPPDirectives", Style.IndentPPDirectives);
+ IO.mapOptional("IndentExternBlock", Style.IndentExternBlock);
IO.mapOptional("IndentWidth", Style.IndentWidth);
IO.mapOptional("IndentWrappedFunctionNames",
Style.IndentWrappedFunctionNames);
@@ -719,6 +731,7 @@ static FormatStyle expandPresets(const FormatStyle &Style) {
Expanded.BraceWrapping.AfterStruct = true;
Expanded.BraceWrapping.AfterUnion = true;
Expanded.BraceWrapping.AfterExternBlock = true;
+ Expanded.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
Expanded.BraceWrapping.SplitEmptyFunction = true;
Expanded.BraceWrapping.SplitEmptyRecord = false;
break;
@@ -738,6 +751,7 @@ static FormatStyle expandPresets(const FormatStyle &Style) {
Expanded.BraceWrapping.AfterStruct = true;
Expanded.BraceWrapping.AfterUnion = true;
Expanded.BraceWrapping.AfterExternBlock = true;
+ Expanded.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
Expanded.BraceWrapping.BeforeCatch = true;
Expanded.BraceWrapping.BeforeElse = true;
break;
@@ -751,6 +765,7 @@ static FormatStyle expandPresets(const FormatStyle &Style) {
Expanded.BraceWrapping.AfterObjCDeclaration = true;
Expanded.BraceWrapping.AfterStruct = true;
Expanded.BraceWrapping.AfterExternBlock = true;
+ Expanded.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
Expanded.BraceWrapping.BeforeCatch = true;
Expanded.BraceWrapping.BeforeElse = true;
Expanded.BraceWrapping.BeforeLambdaBody = true;
@@ -775,6 +790,7 @@ static FormatStyle expandPresets(const FormatStyle &Style) {
/*SplitEmptyFunction=*/true,
/*SplitEmptyRecord=*/true,
/*SplitEmptyNamespace=*/true};
+ Expanded.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
break;
case FormatStyle::BS_WebKit:
Expanded.BraceWrapping.AfterFunction = true;
@@ -834,6 +850,7 @@ FormatStyle getLLVMStyle(FormatStyle::LanguageKind Language) {
/*SplitEmptyFunction=*/true,
/*SplitEmptyRecord=*/true,
/*SplitEmptyNamespace=*/true};
+ LLVMStyle.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
LLVMStyle.BreakAfterJavaFieldAnnotations = false;
LLVMStyle.BreakConstructorInitializers = FormatStyle::BCIS_BeforeColon;
LLVMStyle.BreakInheritanceList = FormatStyle::BILS_BeforeColon;
@@ -1195,6 +1212,7 @@ FormatStyle getMicrosoftStyle(FormatStyle::LanguageKind Language) {
Style.BraceWrapping.AfterObjCDeclaration = true;
Style.BraceWrapping.AfterStruct = true;
Style.BraceWrapping.AfterExternBlock = true;
+ Style.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
Style.BraceWrapping.BeforeCatch = true;
Style.BraceWrapping.BeforeElse = true;
Style.BraceWrapping.BeforeWhile = false;
diff --git a/clang/lib/Format/UnwrappedLineParser.cpp b/clang/lib/Format/UnwrappedLineParser.cpp
index ba509f218ffc..03b6e0c9ef74 100644
--- a/clang/lib/Format/UnwrappedLineParser.cpp
+++ b/clang/lib/Format/UnwrappedLineParser.cpp
@@ -1113,11 +1113,16 @@ void UnwrappedLineParser::parseStructuralElement() {
if (FormatTok->Tok.is(tok::string_literal)) {
nextToken();
if (FormatTok->Tok.is(tok::l_brace)) {
- if (Style.BraceWrapping.AfterExternBlock) {
- addUnwrappedLine();
- parseBlock(/*MustBeDeclaration=*/true);
+ if (!Style.IndentExternBlock) {
+ if (Style.BraceWrapping.AfterExternBlock) {
+ addUnwrappedLine();
+ }
+ parseBlock(/*MustBeDeclaration=*/true,
+ /*AddLevel=*/Style.BraceWrapping.AfterExternBlock);
} else {
- parseBlock(/*MustBeDeclaration=*/true, /*AddLevel=*/false);
+ parseBlock(/*MustBeDeclaration=*/true,
+ /*AddLevel=*/Style.IndentExternBlock ==
+ FormatStyle::IEBS_Indent);
}
addUnwrappedLine();
return;
diff --git a/clang/unittests/Format/FormatTest.cpp b/clang/unittests/Format/FormatTest.cpp
index ff31601e537a..a3b70bfd2824 100644
--- a/clang/unittests/Format/FormatTest.cpp
+++ b/clang/unittests/Format/FormatTest.cpp
@@ -2558,6 +2558,43 @@ TEST_F(FormatTest, FormatsExternC) {
Style);
}
+TEST_F(FormatTest, IndentExternBlockStyle) {
+ FormatStyle Style = getLLVMStyle();
+ Style.IndentWidth = 2;
+
+ Style.IndentExternBlock = FormatStyle::IEBS_Indent;
+ verifyFormat("extern \"C\" { /*9*/\n}", Style);
+ verifyFormat("extern \"C\" {\n"
+ " int foo10();\n"
+ "}",
+ Style);
+
+ Style.IndentExternBlock = FormatStyle::IEBS_NoIndent;
+ verifyFormat("extern \"C\" { /*11*/\n}", Style);
+ verifyFormat("extern \"C\" {\n"
+ "int foo12();\n"
+ "}",
+ Style);
+
+ Style.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
+ Style.BreakBeforeBraces = FormatStyle::BS_Custom;
+ Style.BraceWrapping.AfterExternBlock = true;
+ verifyFormat("extern \"C\"\n{ /*13*/\n}", Style);
+ verifyFormat("extern \"C\"\n{\n"
+ " int foo14();\n"
+ "}",
+ Style);
+
+ Style.IndentExternBlock = FormatStyle::IEBS_AfterExternBlock;
+ Style.BreakBeforeBraces = FormatStyle::BS_Custom;
+ Style.BraceWrapping.AfterExternBlock = false;
+ verifyFormat("extern \"C\" { /*15*/\n}", Style);
+ verifyFormat("extern \"C\" {\n"
+ "int foo16();\n"
+ "}",
+ Style);
+}
+
TEST_F(FormatTest, FormatsInlineASM) {
verifyFormat("asm(\"xyz\" : \"=a\"(a), \"=d\"(b) : \"a\"(data));");
verifyFormat("asm(\"nop\" ::: \"memory\");");
@@ -13846,6 +13883,18 @@ TEST_F(FormatTest, ParsesConfiguration) {
AllowShortIfStatementsOnASingleLine,
FormatStyle::SIS_WithoutElse);
+ Style.IndentExternBlock = FormatStyle::IEBS_NoIndent;
+ CHECK_PARSE("IndentExternBlock: AfterExternBlock", IndentExternBlock,
+ FormatStyle::IEBS_AfterExternBlock);
+ CHECK_PARSE("IndentExternBlock: Indent", IndentExternBlock,
+ FormatStyle::IEBS_Indent);
+ CHECK_PARSE("IndentExternBlock: NoIndent", IndentExternBlock,
+ FormatStyle::IEBS_NoIndent);
+ CHECK_PARSE("IndentExternBlock: true", IndentExternBlock,
+ FormatStyle::IEBS_Indent);
+ CHECK_PARSE("IndentExternBlock: false", IndentExternBlock,
+ FormatStyle::IEBS_NoIndent);
+
// FIXME: This is required because parsing a configuration simply overwrites
// the first N elements of the list instead of resetting it.
Style.ForEachMacros.clear();
More information about the cfe-commits
mailing list