diff --git a/clang/lib/Format/UnwrappedLineParser.cpp b/clang/lib/Format/UnwrappedLineParser.cpp --- a/clang/lib/Format/UnwrappedLineParser.cpp +++ b/clang/lib/Format/UnwrappedLineParser.cpp @@ -324,12 +324,21 @@ } void UnwrappedLineParser::parseCSharpAttribute() { + int UnpairedSquareBrackets = 1; do { switch (FormatTok->Tok.getKind()) { case tok::r_square: nextToken(); - addUnwrappedLine(); - return; + --UnpairedSquareBrackets; + if (UnpairedSquareBrackets == 0) { + addUnwrappedLine(); + return; + } + break; + case tok::l_square: + ++UnpairedSquareBrackets; + nextToken(); + break; default: nextToken(); break; diff --git a/clang/unittests/Format/FormatTestCSharp.cpp b/clang/unittests/Format/FormatTestCSharp.cpp --- a/clang/unittests/Format/FormatTestCSharp.cpp +++ b/clang/unittests/Format/FormatTestCSharp.cpp @@ -273,6 +273,15 @@ "{\n" "}"); + // [] in an attribute do not cause premature line wrapping or indenting. + verifyFormat(R"(// +public class A +{ + [SomeAttribute(new[] { RED, GREEN, BLUE }, -1.0f, 1.0f)] + [DoNotSerialize] + public Data MemberVariable; +})"); + // Unwrappable lines go on a line of their own. // 'target:' is not treated as a label. // Modify Style to enforce a column limit.