llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT--> @llvm/pr-subscribers-clang-format Author: Matthias Görgens (matthiasgoergens) <details> <summary>Changes</summary> `26ffc71afa7c` disallowed breaking on either side of `##` to keep pasted identifiers together, but the blanket rule also caught the GNU comma-swallowing idiom `call(arg, ##__VA_ARGS__)`, so a macro line containing it could never be wrapped and stayed over the column limit. Keep forbidding breaks after `##`, and before `##` except when the previous token is a comma: the comma-`##` sequence swallows the comma rather than pasting tokens, and a backslash-newline between them leaves the token stream unchanged. The two tests cover final and non-final `##__VA_ARGS__` and re-format their own output, pinning idempotence. Fixes #<!-- -->212835. ## Tool use Per the [LLVM AI Tool Use Policy](https://llvm.org/docs/AIToolPolicy.html): AI tools were involved throughout the preparation of this change. I am the author and accountable for the contribution. Assisted-by: OpenAI Codex Assisted-by: Claude Code Assisted-by: Kimi Assisted-by: DeepSeek --- Full diff: https://github.com/llvm/llvm-project/pull/214990.diff 2 Files Affected: - (modified) clang/lib/Format/TokenAnnotator.cpp (+5-1) - (modified) clang/unittests/Format/FormatTest.cpp (+24) ``````````diff diff --git a/clang/lib/Format/TokenAnnotator.cpp b/clang/lib/Format/TokenAnnotator.cpp index b6c33279b0aca..06b28b37582d1 100644 --- a/clang/lib/Format/TokenAnnotator.cpp +++ b/clang/lib/Format/TokenAnnotator.cpp @@ -6511,8 +6511,12 @@ bool TokenAnnotator::canBreakBefore(const AnnotatedLine &Line, !(Right.Next && Right.Next->isOneOf(TT_FunctionDeclarationName, tok::kw_const))); } - if (Left.is(tok::hashhash) || Right.is(tok::hashhash)) + if (Left.is(tok::hashhash)) return false; + // Keep pasted identifiers together, but allow a break before the GNU + // variadic-macro comma-swallowing extension: , ##__VA_ARGS__. + if (Right.is(tok::hashhash)) + return Left.is(tok::comma); if (Right.isOneOf(TT_StartOfName, TT_FunctionDeclarationName, TT_ClassHeadName, TT_QtProperty, tok::kw_operator)) { return true; diff --git a/clang/unittests/Format/FormatTest.cpp b/clang/unittests/Format/FormatTest.cpp index b72a683ac1fff..bce808a0857c9 100644 --- a/clang/unittests/Format/FormatTest.cpp +++ b/clang/unittests/Format/FormatTest.cpp @@ -5985,6 +5985,30 @@ TEST_F(FormatTest, HashInMacroDefinition) { Style); verifyFormat("#define A void # ## #", Style); + auto CommaPasteStyle = getLLVMStyleWithColumns(80); + CommaPasteStyle.IndentWidth = 4; + CommaPasteStyle.ContinuationIndentWidth = 8; + CommaPasteStyle.AlignEscapedNewlines = FormatStyle::ENAS_Right; + verifyFormat( + "#define M(f, ...) " + " \\\n" + " auto f = call(" + "firstArgumentThatIsQuiteLongEnoughToForceAWrapHere11111111, \\\n" + " ##__VA_ARGS__);", + "#define M(f, ...) \\\n" + " auto f = call(" + "firstArgumentThatIsQuiteLongEnoughToForceAWrapHere11111111, " + "##__VA_ARGS__);", + CommaPasteStyle); + CommaPasteStyle.AlignEscapedNewlines = FormatStyle::ENAS_DontAlign; + verifyFormat( + "#define M(...) \\\n" + " call(firstArgumentThatIsQuiteLongEnoughToForceAWrapHere11111111, \\\n" + " ##__VA_ARGS__, extra)", + "#define M(...) \\\n" + " call(firstArgumentThatIsQuiteLongEnoughToForceAWrapHere11111111, " + "##__VA_ARGS__, extra)", + CommaPasteStyle); Style.ColumnLimit = 60; Style.AlignEscapedNewlines = FormatStyle::ENAS_DontAlign; verifyFormat( `````````` </details> https://github.com/llvm/llvm-project/pull/214990 _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
