summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBirunthan Mohanathas <birunthan@mohanathas.com>2015-06-29 15:30:42 +0000
committerBirunthan Mohanathas <birunthan@mohanathas.com>2015-06-29 15:30:42 +0000
commit7180c84364235e70a41db78959cf91294645c73f (patch)
tree104ec5973a14005e3a53fbdd057acecacf900fb4
parentdc04f2073fcf26dfa218d826158213c4aa58d287 (diff)
clang-format: Add option to break after definition return type for top-level functions only
Differential Revision: http://reviews.llvm.org/D10774
-rw-r--r--clang/docs/ClangFormatStyleOptions.rst17
-rw-r--r--clang/include/clang/Format/Format.h19
-rw-r--r--clang/lib/Format/ContinuationIndenter.cpp3
-rw-r--r--clang/lib/Format/Format.cpp18
-rw-r--r--clang/lib/Format/TokenAnnotator.cpp7
-rw-r--r--clang/unittests/Format/FormatTest.cpp46
6 files changed, 85 insertions, 25 deletions
diff --git a/clang/docs/ClangFormatStyleOptions.rst b/clang/docs/ClangFormatStyleOptions.rst
index 837d184a959..ab7bd872ca2 100644
--- a/clang/docs/ClangFormatStyleOptions.rst
+++ b/clang/docs/ClangFormatStyleOptions.rst
@@ -218,12 +218,19 @@ the configuration (without a prefix: ``Auto``).
If ``true``, ``while (true) continue;`` can be put on a
single line.
-**AlwaysBreakAfterDefinitionReturnType** (``bool``)
- If ``true``, always break after function definition return types.
+**AlwaysBreakAfterDefinitionReturnType** (``DefinitionReturnTypeBreakingStyle``)
+ The function definition return type breaking style to use.
+
+ Possible values:
+
+ * ``DRTBS_None`` (in configuration: ``None``)
+ Break after return type automatically.
+ ``PenaltyReturnTypeOnItsOwnLine`` is taken into account.
+ * ``DRTBS_All`` (in configuration: ``All``)
+ Always break after the return type.
+ * ``DRTBS_TopLevel`` (in configuration: ``TopLevel``)
+ Always break after the return types of top level functions.
- More truthfully called 'break before the identifier following the type
- in a function definition'. PenaltyReturnTypeOnItsOwnLine becomes
- irrelevant.
**AlwaysBreakBeforeMultilineStrings** (``bool``)
If ``true``, always break before multiline string literals.
diff --git a/clang/include/clang/Format/Format.h b/clang/include/clang/Format/Format.h
index 66097e0dd50..6f9523cdc1b 100644
--- a/clang/include/clang/Format/Format.h
+++ b/clang/include/clang/Format/Format.h
@@ -112,12 +112,19 @@ struct FormatStyle {
/// single line.
bool AllowShortLoopsOnASingleLine;
- /// \brief If \c true, always break after function definition return types.
- ///
- /// More truthfully called 'break before the identifier following the type
- /// in a function definition'. PenaltyReturnTypeOnItsOwnLine becomes
- /// irrelevant.
- bool AlwaysBreakAfterDefinitionReturnType;
+ /// \brief Different ways to break after the function definition return type.
+ enum DefinitionReturnTypeBreakingStyle {
+ /// Break after return type automatically.
+ /// \c PenaltyReturnTypeOnItsOwnLine is taken into account.
+ DRTBS_None,
+ /// Always break after the return type.
+ DRTBS_All,
+ /// Always break after the return types of top level functions.
+ DRTBS_TopLevel,
+ };
+
+ /// \brief The function definition return type breaking style to use.
+ DefinitionReturnTypeBreakingStyle AlwaysBreakAfterDefinitionReturnType;
/// \brief If \c true, always break before multiline string literals.
///
diff --git a/clang/lib/Format/ContinuationIndenter.cpp b/clang/lib/Format/ContinuationIndenter.cpp
index 2717c2731d2..ed01d689c59 100644
--- a/clang/lib/Format/ContinuationIndenter.cpp
+++ b/clang/lib/Format/ContinuationIndenter.cpp
@@ -126,7 +126,8 @@ bool ContinuationIndenter::canBreak(const LineState &State) {
// Don't break after very short return types (e.g. "void") as that is often
// unexpected.
if (Current.is(TT_FunctionDeclarationName) &&
- !Style.AlwaysBreakAfterDefinitionReturnType && State.Column < 6)
+ Style.AlwaysBreakAfterDefinitionReturnType == FormatStyle::DRTBS_None &&
+ State.Column < 6)
return false;
return !State.Stack.back().NoLineBreak;
diff --git a/clang/lib/Format/Format.cpp b/clang/lib/Format/Format.cpp
index edc44d3e3df..0dd7ca0cbc1 100644
--- a/clang/lib/Format/Format.cpp
+++ b/clang/lib/Format/Format.cpp
@@ -99,6 +99,18 @@ template <> struct ScalarEnumerationTraits<FormatStyle::BraceBreakingStyle> {
}
};
+template <> struct ScalarEnumerationTraits<FormatStyle::DefinitionReturnTypeBreakingStyle> {
+ static void enumeration(IO &IO, FormatStyle::DefinitionReturnTypeBreakingStyle &Value) {
+ IO.enumCase(Value, "None", FormatStyle::DRTBS_None);
+ IO.enumCase(Value, "All", FormatStyle::DRTBS_All);
+ IO.enumCase(Value, "TopLevel", FormatStyle::DRTBS_TopLevel);
+
+ // For backward compatibility.
+ IO.enumCase(Value, "false", FormatStyle::DRTBS_None);
+ IO.enumCase(Value, "true", FormatStyle::DRTBS_All);
+ }
+};
+
template <>
struct ScalarEnumerationTraits<FormatStyle::NamespaceIndentationKind> {
static void enumeration(IO &IO,
@@ -338,7 +350,7 @@ FormatStyle getLLVMStyle() {
LLVMStyle.AllowShortCaseLabelsOnASingleLine = false;
LLVMStyle.AllowShortIfStatementsOnASingleLine = false;
LLVMStyle.AllowShortLoopsOnASingleLine = false;
- LLVMStyle.AlwaysBreakAfterDefinitionReturnType = false;
+ LLVMStyle.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_None;
LLVMStyle.AlwaysBreakBeforeMultilineStrings = false;
LLVMStyle.AlwaysBreakTemplateDeclarations = false;
LLVMStyle.BinPackParameters = true;
@@ -463,6 +475,8 @@ FormatStyle getMozillaStyle() {
FormatStyle MozillaStyle = getLLVMStyle();
MozillaStyle.AllowAllParametersOfDeclarationOnNextLine = false;
MozillaStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Inline;
+ MozillaStyle.AlwaysBreakAfterDefinitionReturnType =
+ FormatStyle::DRTBS_TopLevel;
MozillaStyle.AlwaysBreakTemplateDeclarations = true;
MozillaStyle.BreakConstructorInitializersBeforeComma = true;
MozillaStyle.ConstructorInitializerIndentWidth = 2;
@@ -498,7 +512,7 @@ FormatStyle getWebKitStyle() {
FormatStyle getGNUStyle() {
FormatStyle Style = getLLVMStyle();
- Style.AlwaysBreakAfterDefinitionReturnType = true;
+ Style.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_All;
Style.BreakBeforeBinaryOperators = FormatStyle::BOS_All;
Style.BreakBeforeBraces = FormatStyle::BS_GNU;
Style.BreakBeforeTernaryOperators = true;
diff --git a/clang/lib/Format/TokenAnnotator.cpp b/clang/lib/Format/TokenAnnotator.cpp
index 2f1aae39344..0117f222004 100644
--- a/clang/lib/Format/TokenAnnotator.cpp
+++ b/clang/lib/Format/TokenAnnotator.cpp
@@ -1539,8 +1539,11 @@ void TokenAnnotator::calculateFormattingInformation(AnnotatedLine &Line) {
Current->MustBreakBefore =
Current->MustBreakBefore || mustBreakBefore(Line, *Current);
- if (Style.AlwaysBreakAfterDefinitionReturnType && InFunctionDecl &&
- Current->is(TT_FunctionDeclarationName) &&
+ if ((Style.AlwaysBreakAfterDefinitionReturnType == FormatStyle::DRTBS_All ||
+ (Style.AlwaysBreakAfterDefinitionReturnType ==
+ FormatStyle::DRTBS_TopLevel &&
+ Line.Level == 0)) &&
+ InFunctionDecl && Current->is(TT_FunctionDeclarationName) &&
!Line.Last->isOneOf(tok::semi, tok::comment)) // Only for definitions.
// FIXME: Line.Last points to other characters than tok::semi
// and tok::lbrace.
diff --git a/clang/unittests/Format/FormatTest.cpp b/clang/unittests/Format/FormatTest.cpp
index 6b8bff167ab..743171fb003 100644
--- a/clang/unittests/Format/FormatTest.cpp
+++ b/clang/unittests/Format/FormatTest.cpp
@@ -4618,30 +4618,50 @@ TEST_F(FormatTest, AlignsStringLiterals) {
" \"c\";");
}
-TEST_F(FormatTest, AlwaysBreakAfterDefinitionReturnType) {
- FormatStyle AfterType = getLLVMStyle();
- AfterType.AlwaysBreakAfterDefinitionReturnType = true;
+TEST_F(FormatTest, DefinitionReturnTypeBreakingStyle) {
+ FormatStyle Style = getLLVMStyle();
+ Style.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_TopLevel;
+ verifyFormat("class C {\n"
+ " int f() { return 1; }\n"
+ "};\n"
+ "int\n"
+ "f() {\n"
+ " return 1;\n"
+ "}",
+ Style);
+ Style.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_All;
+ verifyFormat("class C {\n"
+ " int\n"
+ " f() {\n"
+ " return 1;\n"
+ " }\n"
+ "};\n"
+ "int\n"
+ "f() {\n"
+ " return 1;\n"
+ "}",
+ Style);
verifyFormat("const char *\n"
"f(void) {\n" // Break here.
" return \"\";\n"
"}\n"
"const char *bar(void);\n", // No break here.
- AfterType);
+ Style);
verifyFormat("template <class T>\n"
"T *\n"
"f(T &c) {\n" // Break here.
" return NULL;\n"
"}\n"
"template <class T> T *f(T &c);\n", // No break here.
- AfterType);
- AfterType.BreakBeforeBraces = FormatStyle::BS_Stroustrup;
+ Style);
+ Style.BreakBeforeBraces = FormatStyle::BS_Stroustrup;
verifyFormat("const char *\n"
"f(void)\n" // Break here.
"{\n"
" return \"\";\n"
"}\n"
"const char *bar(void);\n", // No break here.
- AfterType);
+ Style);
verifyFormat("template <class T>\n"
"T *\n" // Problem here: no line break
"f(T &c)\n" // Break here.
@@ -4649,7 +4669,7 @@ TEST_F(FormatTest, AlwaysBreakAfterDefinitionReturnType) {
" return NULL;\n"
"}\n"
"template <class T> T *f(T &c);\n", // No break here.
- AfterType);
+ Style);
}
TEST_F(FormatTest, AlwaysBreakBeforeMultilineStrings) {
@@ -9041,7 +9061,6 @@ TEST_F(FormatTest, ParsesConfigurationBools) {
CHECK_PARSE_BOOL(AllowShortCaseLabelsOnASingleLine);
CHECK_PARSE_BOOL(AllowShortIfStatementsOnASingleLine);
CHECK_PARSE_BOOL(AllowShortLoopsOnASingleLine);
- CHECK_PARSE_BOOL(AlwaysBreakAfterDefinitionReturnType);
CHECK_PARSE_BOOL(AlwaysBreakTemplateDeclarations);
CHECK_PARSE_BOOL(BinPackParameters);
CHECK_PARSE_BOOL(BinPackArguments);
@@ -9174,6 +9193,15 @@ TEST_F(FormatTest, ParsesConfiguration) {
FormatStyle::BS_Allman);
CHECK_PARSE("BreakBeforeBraces: GNU", BreakBeforeBraces, FormatStyle::BS_GNU);
+ Style.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_All;
+ CHECK_PARSE("AlwaysBreakAfterDefinitionReturnType: None",
+ AlwaysBreakAfterDefinitionReturnType, FormatStyle::DRTBS_None);
+ CHECK_PARSE("AlwaysBreakAfterDefinitionReturnType: All",
+ AlwaysBreakAfterDefinitionReturnType, FormatStyle::DRTBS_All);
+ CHECK_PARSE("AlwaysBreakAfterDefinitionReturnType: TopLevel",
+ AlwaysBreakAfterDefinitionReturnType,
+ FormatStyle::DRTBS_TopLevel);
+
Style.NamespaceIndentation = FormatStyle::NI_All;
CHECK_PARSE("NamespaceIndentation: None", NamespaceIndentation,
FormatStyle::NI_None);