clang 19.0.0git
Format.cpp
Go to the documentation of this file.
1//===--- Format.cpp - Format C++ code -------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8///
9/// \file
10/// This file implements functions declared in Format.h. This will be
11/// split into separate files as we go.
12///
13//===----------------------------------------------------------------------===//
14
15#include "clang/Format/Format.h"
25#include "llvm/ADT/Sequence.h"
26
27#define DEBUG_TYPE "format-formatter"
28
30
31LLVM_YAML_IS_SEQUENCE_VECTOR(clang::format::FormatStyle::RawStringFormat)
32
33namespace llvm {
34namespace yaml {
35template <>
36struct ScalarEnumerationTraits<FormatStyle::BreakBeforeNoexceptSpecifierStyle> {
37 static void
38 enumeration(IO &IO, FormatStyle::BreakBeforeNoexceptSpecifierStyle &Value) {
39 IO.enumCase(Value, "Never", FormatStyle::BBNSS_Never);
40 IO.enumCase(Value, "OnlyWithParen", FormatStyle::BBNSS_OnlyWithParen);
41 IO.enumCase(Value, "Always", FormatStyle::BBNSS_Always);
42 }
43};
44
45template <> struct MappingTraits<FormatStyle::AlignConsecutiveStyle> {
46 static void enumInput(IO &IO, FormatStyle::AlignConsecutiveStyle &Value) {
47 IO.enumCase(Value, "None",
48 FormatStyle::AlignConsecutiveStyle(
49 {/*Enabled=*/false, /*AcrossEmptyLines=*/false,
50 /*AcrossComments=*/false, /*AlignCompound=*/false,
51 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
52 IO.enumCase(Value, "Consecutive",
53 FormatStyle::AlignConsecutiveStyle(
54 {/*Enabled=*/true, /*AcrossEmptyLines=*/false,
55 /*AcrossComments=*/false, /*AlignCompound=*/false,
56 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
57 IO.enumCase(Value, "AcrossEmptyLines",
58 FormatStyle::AlignConsecutiveStyle(
59 {/*Enabled=*/true, /*AcrossEmptyLines=*/true,
60 /*AcrossComments=*/false, /*AlignCompound=*/false,
61 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
62 IO.enumCase(Value, "AcrossComments",
63 FormatStyle::AlignConsecutiveStyle(
64 {/*Enabled=*/true, /*AcrossEmptyLines=*/false,
65 /*AcrossComments=*/true, /*AlignCompound=*/false,
66 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
67 IO.enumCase(Value, "AcrossEmptyLinesAndComments",
68 FormatStyle::AlignConsecutiveStyle(
69 {/*Enabled=*/true, /*AcrossEmptyLines=*/true,
70 /*AcrossComments=*/true, /*AlignCompound=*/false,
71 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
72
73 // For backward compatibility.
74 IO.enumCase(Value, "true",
75 FormatStyle::AlignConsecutiveStyle(
76 {/*Enabled=*/true, /*AcrossEmptyLines=*/false,
77 /*AcrossComments=*/false, /*AlignCompound=*/false,
78 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
79 IO.enumCase(Value, "false",
80 FormatStyle::AlignConsecutiveStyle(
81 {/*Enabled=*/false, /*AcrossEmptyLines=*/false,
82 /*AcrossComments=*/false, /*AlignCompound=*/false,
83 /*AlignFunctionPointers=*/false, /*PadOperators=*/true}));
84 }
85
86 static void mapping(IO &IO, FormatStyle::AlignConsecutiveStyle &Value) {
87 IO.mapOptional("Enabled", Value.Enabled);
88 IO.mapOptional("AcrossEmptyLines", Value.AcrossEmptyLines);
89 IO.mapOptional("AcrossComments", Value.AcrossComments);
90 IO.mapOptional("AlignCompound", Value.AlignCompound);
91 IO.mapOptional("AlignFunctionPointers", Value.AlignFunctionPointers);
92 IO.mapOptional("PadOperators", Value.PadOperators);
93 }
94};
95
96template <>
97struct MappingTraits<FormatStyle::ShortCaseStatementsAlignmentStyle> {
98 static void mapping(IO &IO,
99 FormatStyle::ShortCaseStatementsAlignmentStyle &Value) {
100 IO.mapOptional("Enabled", Value.Enabled);
101 IO.mapOptional("AcrossEmptyLines", Value.AcrossEmptyLines);
102 IO.mapOptional("AcrossComments", Value.AcrossComments);
103 IO.mapOptional("AlignCaseArrows", Value.AlignCaseArrows);
104 IO.mapOptional("AlignCaseColons", Value.AlignCaseColons);
105 }
106};
107
108template <>
109struct ScalarEnumerationTraits<FormatStyle::AttributeBreakingStyle> {
110 static void enumeration(IO &IO, FormatStyle::AttributeBreakingStyle &Value) {
111 IO.enumCase(Value, "Always", FormatStyle::ABS_Always);
112 IO.enumCase(Value, "Leave", FormatStyle::ABS_Leave);
113 IO.enumCase(Value, "Never", FormatStyle::ABS_Never);
114 }
115};
116
117template <>
118struct ScalarEnumerationTraits<FormatStyle::ArrayInitializerAlignmentStyle> {
119 static void enumeration(IO &IO,
120 FormatStyle::ArrayInitializerAlignmentStyle &Value) {
121 IO.enumCase(Value, "None", FormatStyle::AIAS_None);
122 IO.enumCase(Value, "Left", FormatStyle::AIAS_Left);
123 IO.enumCase(Value, "Right", FormatStyle::AIAS_Right);
124 }
125};
126
127template <> struct ScalarEnumerationTraits<FormatStyle::BinaryOperatorStyle> {
128 static void enumeration(IO &IO, FormatStyle::BinaryOperatorStyle &Value) {
129 IO.enumCase(Value, "All", FormatStyle::BOS_All);
130 IO.enumCase(Value, "true", FormatStyle::BOS_All);
131 IO.enumCase(Value, "None", FormatStyle::BOS_None);
132 IO.enumCase(Value, "false", FormatStyle::BOS_None);
133 IO.enumCase(Value, "NonAssignment", FormatStyle::BOS_NonAssignment);
134 }
135};
136
137template <> struct ScalarEnumerationTraits<FormatStyle::BinPackStyle> {
138 static void enumeration(IO &IO, FormatStyle::BinPackStyle &Value) {
139 IO.enumCase(Value, "Auto", FormatStyle::BPS_Auto);
140 IO.enumCase(Value, "Always", FormatStyle::BPS_Always);
141 IO.enumCase(Value, "Never", FormatStyle::BPS_Never);
142 }
143};
144
145template <>
146struct ScalarEnumerationTraits<FormatStyle::BitFieldColonSpacingStyle> {
147 static void enumeration(IO &IO,
148 FormatStyle::BitFieldColonSpacingStyle &Value) {
149 IO.enumCase(Value, "Both", FormatStyle::BFCS_Both);
150 IO.enumCase(Value, "None", FormatStyle::BFCS_None);
151 IO.enumCase(Value, "Before", FormatStyle::BFCS_Before);
152 IO.enumCase(Value, "After", FormatStyle::BFCS_After);
153 }
154};
155
156template <> struct ScalarEnumerationTraits<FormatStyle::BraceBreakingStyle> {
157 static void enumeration(IO &IO, FormatStyle::BraceBreakingStyle &Value) {
158 IO.enumCase(Value, "Attach", FormatStyle::BS_Attach);
159 IO.enumCase(Value, "Linux", FormatStyle::BS_Linux);
160 IO.enumCase(Value, "Mozilla", FormatStyle::BS_Mozilla);
161 IO.enumCase(Value, "Stroustrup", FormatStyle::BS_Stroustrup);
162 IO.enumCase(Value, "Allman", FormatStyle::BS_Allman);
163 IO.enumCase(Value, "Whitesmiths", FormatStyle::BS_Whitesmiths);
164 IO.enumCase(Value, "GNU", FormatStyle::BS_GNU);
165 IO.enumCase(Value, "WebKit", FormatStyle::BS_WebKit);
166 IO.enumCase(Value, "Custom", FormatStyle::BS_Custom);
167 }
168};
169
170template <> struct MappingTraits<FormatStyle::BraceWrappingFlags> {
171 static void mapping(IO &IO, FormatStyle::BraceWrappingFlags &Wrapping) {
172 IO.mapOptional("AfterCaseLabel", Wrapping.AfterCaseLabel);
173 IO.mapOptional("AfterClass", Wrapping.AfterClass);
174 IO.mapOptional("AfterControlStatement", Wrapping.AfterControlStatement);
175 IO.mapOptional("AfterEnum", Wrapping.AfterEnum);
176 IO.mapOptional("AfterExternBlock", Wrapping.AfterExternBlock);
177 IO.mapOptional("AfterFunction", Wrapping.AfterFunction);
178 IO.mapOptional("AfterNamespace", Wrapping.AfterNamespace);
179 IO.mapOptional("AfterObjCDeclaration", Wrapping.AfterObjCDeclaration);
180 IO.mapOptional("AfterStruct", Wrapping.AfterStruct);
181 IO.mapOptional("AfterUnion", Wrapping.AfterUnion);
182 IO.mapOptional("BeforeCatch", Wrapping.BeforeCatch);
183 IO.mapOptional("BeforeElse", Wrapping.BeforeElse);
184 IO.mapOptional("BeforeLambdaBody", Wrapping.BeforeLambdaBody);
185 IO.mapOptional("BeforeWhile", Wrapping.BeforeWhile);
186 IO.mapOptional("IndentBraces", Wrapping.IndentBraces);
187 IO.mapOptional("SplitEmptyFunction", Wrapping.SplitEmptyFunction);
188 IO.mapOptional("SplitEmptyRecord", Wrapping.SplitEmptyRecord);
189 IO.mapOptional("SplitEmptyNamespace", Wrapping.SplitEmptyNamespace);
190 }
191};
192
193template <> struct ScalarEnumerationTraits<FormatStyle::BracketAlignmentStyle> {
194 static void enumeration(IO &IO, FormatStyle::BracketAlignmentStyle &Value) {
195 IO.enumCase(Value, "Align", FormatStyle::BAS_Align);
196 IO.enumCase(Value, "DontAlign", FormatStyle::BAS_DontAlign);
197 IO.enumCase(Value, "AlwaysBreak", FormatStyle::BAS_AlwaysBreak);
198 IO.enumCase(Value, "BlockIndent", FormatStyle::BAS_BlockIndent);
199
200 // For backward compatibility.
201 IO.enumCase(Value, "true", FormatStyle::BAS_Align);
202 IO.enumCase(Value, "false", FormatStyle::BAS_DontAlign);
203 }
204};
205
206template <>
207struct ScalarEnumerationTraits<
208 FormatStyle::BraceWrappingAfterControlStatementStyle> {
209 static void
211 FormatStyle::BraceWrappingAfterControlStatementStyle &Value) {
212 IO.enumCase(Value, "Never", FormatStyle::BWACS_Never);
213 IO.enumCase(Value, "MultiLine", FormatStyle::BWACS_MultiLine);
214 IO.enumCase(Value, "Always", FormatStyle::BWACS_Always);
215
216 // For backward compatibility.
217 IO.enumCase(Value, "false", FormatStyle::BWACS_Never);
218 IO.enumCase(Value, "true", FormatStyle::BWACS_Always);
219 }
220};
221
222template <>
223struct ScalarEnumerationTraits<
224 FormatStyle::BreakBeforeConceptDeclarationsStyle> {
225 static void
226 enumeration(IO &IO, FormatStyle::BreakBeforeConceptDeclarationsStyle &Value) {
227 IO.enumCase(Value, "Never", FormatStyle::BBCDS_Never);
228 IO.enumCase(Value, "Allowed", FormatStyle::BBCDS_Allowed);
229 IO.enumCase(Value, "Always", FormatStyle::BBCDS_Always);
230
231 // For backward compatibility.
232 IO.enumCase(Value, "true", FormatStyle::BBCDS_Always);
233 IO.enumCase(Value, "false", FormatStyle::BBCDS_Allowed);
234 }
235};
236
237template <>
238struct ScalarEnumerationTraits<FormatStyle::BreakBeforeInlineASMColonStyle> {
239 static void enumeration(IO &IO,
240 FormatStyle::BreakBeforeInlineASMColonStyle &Value) {
241 IO.enumCase(Value, "Never", FormatStyle::BBIAS_Never);
242 IO.enumCase(Value, "OnlyMultiline", FormatStyle::BBIAS_OnlyMultiline);
243 IO.enumCase(Value, "Always", FormatStyle::BBIAS_Always);
244 }
245};
246
247template <>
248struct ScalarEnumerationTraits<FormatStyle::BreakConstructorInitializersStyle> {
249 static void
250 enumeration(IO &IO, FormatStyle::BreakConstructorInitializersStyle &Value) {
251 IO.enumCase(Value, "BeforeColon", FormatStyle::BCIS_BeforeColon);
252 IO.enumCase(Value, "BeforeComma", FormatStyle::BCIS_BeforeComma);
253 IO.enumCase(Value, "AfterColon", FormatStyle::BCIS_AfterColon);
254 }
255};
256
257template <>
258struct ScalarEnumerationTraits<FormatStyle::BreakInheritanceListStyle> {
259 static void enumeration(IO &IO,
260 FormatStyle::BreakInheritanceListStyle &Value) {
261 IO.enumCase(Value, "BeforeColon", FormatStyle::BILS_BeforeColon);
262 IO.enumCase(Value, "BeforeComma", FormatStyle::BILS_BeforeComma);
263 IO.enumCase(Value, "AfterColon", FormatStyle::BILS_AfterColon);
264 IO.enumCase(Value, "AfterComma", FormatStyle::BILS_AfterComma);
265 }
266};
267
268template <>
269struct ScalarEnumerationTraits<FormatStyle::BreakTemplateDeclarationsStyle> {
270 static void enumeration(IO &IO,
271 FormatStyle::BreakTemplateDeclarationsStyle &Value) {
272 IO.enumCase(Value, "Leave", FormatStyle::BTDS_Leave);
273 IO.enumCase(Value, "No", FormatStyle::BTDS_No);
274 IO.enumCase(Value, "MultiLine", FormatStyle::BTDS_MultiLine);
275 IO.enumCase(Value, "Yes", FormatStyle::BTDS_Yes);
276
277 // For backward compatibility.
278 IO.enumCase(Value, "false", FormatStyle::BTDS_MultiLine);
279 IO.enumCase(Value, "true", FormatStyle::BTDS_Yes);
280 }
281};
282
283template <> struct ScalarEnumerationTraits<FormatStyle::DAGArgStyle> {
284 static void enumeration(IO &IO, FormatStyle::DAGArgStyle &Value) {
285 IO.enumCase(Value, "DontBreak", FormatStyle::DAS_DontBreak);
286 IO.enumCase(Value, "BreakElements", FormatStyle::DAS_BreakElements);
287 IO.enumCase(Value, "BreakAll", FormatStyle::DAS_BreakAll);
288 }
289};
290
291template <>
292struct ScalarEnumerationTraits<FormatStyle::DefinitionReturnTypeBreakingStyle> {
293 static void
294 enumeration(IO &IO, FormatStyle::DefinitionReturnTypeBreakingStyle &Value) {
295 IO.enumCase(Value, "None", FormatStyle::DRTBS_None);
296 IO.enumCase(Value, "All", FormatStyle::DRTBS_All);
297 IO.enumCase(Value, "TopLevel", FormatStyle::DRTBS_TopLevel);
298
299 // For backward compatibility.
300 IO.enumCase(Value, "false", FormatStyle::DRTBS_None);
301 IO.enumCase(Value, "true", FormatStyle::DRTBS_All);
302 }
303};
304
305template <>
306struct ScalarEnumerationTraits<FormatStyle::EscapedNewlineAlignmentStyle> {
307 static void enumeration(IO &IO,
308 FormatStyle::EscapedNewlineAlignmentStyle &Value) {
309 IO.enumCase(Value, "DontAlign", FormatStyle::ENAS_DontAlign);
310 IO.enumCase(Value, "Left", FormatStyle::ENAS_Left);
311 IO.enumCase(Value, "Right", FormatStyle::ENAS_Right);
312
313 // For backward compatibility.
314 IO.enumCase(Value, "true", FormatStyle::ENAS_Left);
315 IO.enumCase(Value, "false", FormatStyle::ENAS_Right);
316 }
317};
318
319template <>
320struct ScalarEnumerationTraits<FormatStyle::EmptyLineAfterAccessModifierStyle> {
321 static void
322 enumeration(IO &IO, FormatStyle::EmptyLineAfterAccessModifierStyle &Value) {
323 IO.enumCase(Value, "Never", FormatStyle::ELAAMS_Never);
324 IO.enumCase(Value, "Leave", FormatStyle::ELAAMS_Leave);
325 IO.enumCase(Value, "Always", FormatStyle::ELAAMS_Always);
326 }
327};
328
329template <>
330struct ScalarEnumerationTraits<
331 FormatStyle::EmptyLineBeforeAccessModifierStyle> {
332 static void
333 enumeration(IO &IO, FormatStyle::EmptyLineBeforeAccessModifierStyle &Value) {
334 IO.enumCase(Value, "Never", FormatStyle::ELBAMS_Never);
335 IO.enumCase(Value, "Leave", FormatStyle::ELBAMS_Leave);
336 IO.enumCase(Value, "LogicalBlock", FormatStyle::ELBAMS_LogicalBlock);
337 IO.enumCase(Value, "Always", FormatStyle::ELBAMS_Always);
338 }
339};
340
341template <>
342struct ScalarEnumerationTraits<FormatStyle::IndentExternBlockStyle> {
343 static void enumeration(IO &IO, FormatStyle::IndentExternBlockStyle &Value) {
344 IO.enumCase(Value, "AfterExternBlock", FormatStyle::IEBS_AfterExternBlock);
345 IO.enumCase(Value, "Indent", FormatStyle::IEBS_Indent);
346 IO.enumCase(Value, "NoIndent", FormatStyle::IEBS_NoIndent);
347 IO.enumCase(Value, "true", FormatStyle::IEBS_Indent);
348 IO.enumCase(Value, "false", FormatStyle::IEBS_NoIndent);
349 }
350};
351
352template <> struct MappingTraits<FormatStyle::IntegerLiteralSeparatorStyle> {
353 static void mapping(IO &IO, FormatStyle::IntegerLiteralSeparatorStyle &Base) {
354 IO.mapOptional("Binary", Base.Binary);
355 IO.mapOptional("BinaryMinDigits", Base.BinaryMinDigits);
356 IO.mapOptional("Decimal", Base.Decimal);
357 IO.mapOptional("DecimalMinDigits", Base.DecimalMinDigits);
358 IO.mapOptional("Hex", Base.Hex);
359 IO.mapOptional("HexMinDigits", Base.HexMinDigits);
360 }
361};
362
363template <> struct ScalarEnumerationTraits<FormatStyle::JavaScriptQuoteStyle> {
364 static void enumeration(IO &IO, FormatStyle::JavaScriptQuoteStyle &Value) {
365 IO.enumCase(Value, "Leave", FormatStyle::JSQS_Leave);
366 IO.enumCase(Value, "Single", FormatStyle::JSQS_Single);
367 IO.enumCase(Value, "Double", FormatStyle::JSQS_Double);
368 }
369};
370
371template <> struct ScalarEnumerationTraits<FormatStyle::LanguageKind> {
372 static void enumeration(IO &IO, FormatStyle::LanguageKind &Value) {
373 IO.enumCase(Value, "Cpp", FormatStyle::LK_Cpp);
374 IO.enumCase(Value, "Java", FormatStyle::LK_Java);
375 IO.enumCase(Value, "JavaScript", FormatStyle::LK_JavaScript);
376 IO.enumCase(Value, "ObjC", FormatStyle::LK_ObjC);
377 IO.enumCase(Value, "Proto", FormatStyle::LK_Proto);
378 IO.enumCase(Value, "TableGen", FormatStyle::LK_TableGen);
379 IO.enumCase(Value, "TextProto", FormatStyle::LK_TextProto);
380 IO.enumCase(Value, "CSharp", FormatStyle::LK_CSharp);
381 IO.enumCase(Value, "Json", FormatStyle::LK_Json);
382 IO.enumCase(Value, "Verilog", FormatStyle::LK_Verilog);
383 }
384};
385
386template <> struct ScalarEnumerationTraits<FormatStyle::LanguageStandard> {
387 static void enumeration(IO &IO, FormatStyle::LanguageStandard &Value) {
388 IO.enumCase(Value, "c++03", FormatStyle::LS_Cpp03);
389 IO.enumCase(Value, "C++03", FormatStyle::LS_Cpp03); // Legacy alias
390 IO.enumCase(Value, "Cpp03", FormatStyle::LS_Cpp03); // Legacy alias
391
392 IO.enumCase(Value, "c++11", FormatStyle::LS_Cpp11);
393 IO.enumCase(Value, "C++11", FormatStyle::LS_Cpp11); // Legacy alias
394
395 IO.enumCase(Value, "c++14", FormatStyle::LS_Cpp14);
396 IO.enumCase(Value, "c++17", FormatStyle::LS_Cpp17);
397 IO.enumCase(Value, "c++20", FormatStyle::LS_Cpp20);
398
399 IO.enumCase(Value, "Latest", FormatStyle::LS_Latest);
400 IO.enumCase(Value, "Cpp11", FormatStyle::LS_Latest); // Legacy alias
401 IO.enumCase(Value, "Auto", FormatStyle::LS_Auto);
402 }
403};
404
405template <>
406struct ScalarEnumerationTraits<FormatStyle::LambdaBodyIndentationKind> {
407 static void enumeration(IO &IO,
408 FormatStyle::LambdaBodyIndentationKind &Value) {
409 IO.enumCase(Value, "Signature", FormatStyle::LBI_Signature);
410 IO.enumCase(Value, "OuterScope", FormatStyle::LBI_OuterScope);
411 }
412};
413
414template <> struct ScalarEnumerationTraits<FormatStyle::LineEndingStyle> {
415 static void enumeration(IO &IO, FormatStyle::LineEndingStyle &Value) {
416 IO.enumCase(Value, "LF", FormatStyle::LE_LF);
417 IO.enumCase(Value, "CRLF", FormatStyle::LE_CRLF);
418 IO.enumCase(Value, "DeriveLF", FormatStyle::LE_DeriveLF);
419 IO.enumCase(Value, "DeriveCRLF", FormatStyle::LE_DeriveCRLF);
420 }
421};
422
423template <>
424struct ScalarEnumerationTraits<FormatStyle::NamespaceIndentationKind> {
425 static void enumeration(IO &IO,
426 FormatStyle::NamespaceIndentationKind &Value) {
427 IO.enumCase(Value, "None", FormatStyle::NI_None);
428 IO.enumCase(Value, "Inner", FormatStyle::NI_Inner);
429 IO.enumCase(Value, "All", FormatStyle::NI_All);
430 }
431};
432
433template <> struct ScalarEnumerationTraits<FormatStyle::OperandAlignmentStyle> {
434 static void enumeration(IO &IO, FormatStyle::OperandAlignmentStyle &Value) {
435 IO.enumCase(Value, "DontAlign", FormatStyle::OAS_DontAlign);
436 IO.enumCase(Value, "Align", FormatStyle::OAS_Align);
437 IO.enumCase(Value, "AlignAfterOperator",
438 FormatStyle::OAS_AlignAfterOperator);
439
440 // For backward compatibility.
441 IO.enumCase(Value, "true", FormatStyle::OAS_Align);
442 IO.enumCase(Value, "false", FormatStyle::OAS_DontAlign);
443 }
444};
445
446template <>
447struct ScalarEnumerationTraits<FormatStyle::PackConstructorInitializersStyle> {
448 static void
449 enumeration(IO &IO, FormatStyle::PackConstructorInitializersStyle &Value) {
450 IO.enumCase(Value, "Never", FormatStyle::PCIS_Never);
451 IO.enumCase(Value, "BinPack", FormatStyle::PCIS_BinPack);
452 IO.enumCase(Value, "CurrentLine", FormatStyle::PCIS_CurrentLine);
453 IO.enumCase(Value, "NextLine", FormatStyle::PCIS_NextLine);
454 IO.enumCase(Value, "NextLineOnly", FormatStyle::PCIS_NextLineOnly);
455 }
456};
457
458template <> struct ScalarEnumerationTraits<FormatStyle::PointerAlignmentStyle> {
459 static void enumeration(IO &IO, FormatStyle::PointerAlignmentStyle &Value) {
460 IO.enumCase(Value, "Middle", FormatStyle::PAS_Middle);
461 IO.enumCase(Value, "Left", FormatStyle::PAS_Left);
462 IO.enumCase(Value, "Right", FormatStyle::PAS_Right);
463
464 // For backward compatibility.
465 IO.enumCase(Value, "true", FormatStyle::PAS_Left);
466 IO.enumCase(Value, "false", FormatStyle::PAS_Right);
467 }
468};
469
470template <>
471struct ScalarEnumerationTraits<FormatStyle::PPDirectiveIndentStyle> {
472 static void enumeration(IO &IO, FormatStyle::PPDirectiveIndentStyle &Value) {
473 IO.enumCase(Value, "None", FormatStyle::PPDIS_None);
474 IO.enumCase(Value, "AfterHash", FormatStyle::PPDIS_AfterHash);
475 IO.enumCase(Value, "BeforeHash", FormatStyle::PPDIS_BeforeHash);
476 }
477};
478
479template <>
480struct ScalarEnumerationTraits<FormatStyle::QualifierAlignmentStyle> {
481 static void enumeration(IO &IO, FormatStyle::QualifierAlignmentStyle &Value) {
482 IO.enumCase(Value, "Leave", FormatStyle::QAS_Leave);
483 IO.enumCase(Value, "Left", FormatStyle::QAS_Left);
484 IO.enumCase(Value, "Right", FormatStyle::QAS_Right);
485 IO.enumCase(Value, "Custom", FormatStyle::QAS_Custom);
486 }
487};
488
489template <> struct MappingTraits<FormatStyle::RawStringFormat> {
490 static void mapping(IO &IO, FormatStyle::RawStringFormat &Format) {
491 IO.mapOptional("Language", Format.Language);
492 IO.mapOptional("Delimiters", Format.Delimiters);
493 IO.mapOptional("EnclosingFunctions", Format.EnclosingFunctions);
494 IO.mapOptional("CanonicalDelimiter", Format.CanonicalDelimiter);
495 IO.mapOptional("BasedOnStyle", Format.BasedOnStyle);
496 }
497};
498
499template <>
500struct ScalarEnumerationTraits<FormatStyle::ReferenceAlignmentStyle> {
501 static void enumeration(IO &IO, FormatStyle::ReferenceAlignmentStyle &Value) {
502 IO.enumCase(Value, "Pointer", FormatStyle::RAS_Pointer);
503 IO.enumCase(Value, "Middle", FormatStyle::RAS_Middle);
504 IO.enumCase(Value, "Left", FormatStyle::RAS_Left);
505 IO.enumCase(Value, "Right", FormatStyle::RAS_Right);
506 }
507};
508
509template <>
510struct ScalarEnumerationTraits<FormatStyle::RemoveParenthesesStyle> {
511 static void enumeration(IO &IO, FormatStyle::RemoveParenthesesStyle &Value) {
512 IO.enumCase(Value, "Leave", FormatStyle::RPS_Leave);
513 IO.enumCase(Value, "MultipleParentheses",
514 FormatStyle::RPS_MultipleParentheses);
515 IO.enumCase(Value, "ReturnStatement", FormatStyle::RPS_ReturnStatement);
516 }
517};
518
519template <>
520struct ScalarEnumerationTraits<FormatStyle::RequiresClausePositionStyle> {
521 static void enumeration(IO &IO,
522 FormatStyle::RequiresClausePositionStyle &Value) {
523 IO.enumCase(Value, "OwnLine", FormatStyle::RCPS_OwnLine);
524 IO.enumCase(Value, "WithPreceding", FormatStyle::RCPS_WithPreceding);
525 IO.enumCase(Value, "WithFollowing", FormatStyle::RCPS_WithFollowing);
526 IO.enumCase(Value, "SingleLine", FormatStyle::RCPS_SingleLine);
527 }
528};
529
530template <>
531struct ScalarEnumerationTraits<FormatStyle::RequiresExpressionIndentationKind> {
532 static void
533 enumeration(IO &IO, FormatStyle::RequiresExpressionIndentationKind &Value) {
534 IO.enumCase(Value, "Keyword", FormatStyle::REI_Keyword);
535 IO.enumCase(Value, "OuterScope", FormatStyle::REI_OuterScope);
536 }
537};
538
539template <>
540struct ScalarEnumerationTraits<FormatStyle::ReturnTypeBreakingStyle> {
541 static void enumeration(IO &IO, FormatStyle::ReturnTypeBreakingStyle &Value) {
542 IO.enumCase(Value, "None", FormatStyle::RTBS_None);
543 IO.enumCase(Value, "Automatic", FormatStyle::RTBS_Automatic);
544 IO.enumCase(Value, "ExceptShortType", FormatStyle::RTBS_ExceptShortType);
545 IO.enumCase(Value, "All", FormatStyle::RTBS_All);
546 IO.enumCase(Value, "TopLevel", FormatStyle::RTBS_TopLevel);
547 IO.enumCase(Value, "TopLevelDefinitions",
548 FormatStyle::RTBS_TopLevelDefinitions);
549 IO.enumCase(Value, "AllDefinitions", FormatStyle::RTBS_AllDefinitions);
550 }
551};
552
553template <>
554struct ScalarEnumerationTraits<FormatStyle::SeparateDefinitionStyle> {
555 static void enumeration(IO &IO, FormatStyle::SeparateDefinitionStyle &Value) {
556 IO.enumCase(Value, "Leave", FormatStyle::SDS_Leave);
557 IO.enumCase(Value, "Always", FormatStyle::SDS_Always);
558 IO.enumCase(Value, "Never", FormatStyle::SDS_Never);
559 }
560};
561
562template <> struct ScalarEnumerationTraits<FormatStyle::ShortBlockStyle> {
563 static void enumeration(IO &IO, FormatStyle::ShortBlockStyle &Value) {
564 IO.enumCase(Value, "Never", FormatStyle::SBS_Never);
565 IO.enumCase(Value, "false", FormatStyle::SBS_Never);
566 IO.enumCase(Value, "Always", FormatStyle::SBS_Always);
567 IO.enumCase(Value, "true", FormatStyle::SBS_Always);
568 IO.enumCase(Value, "Empty", FormatStyle::SBS_Empty);
569 }
570};
571
572template <> struct ScalarEnumerationTraits<FormatStyle::ShortFunctionStyle> {
573 static void enumeration(IO &IO, FormatStyle::ShortFunctionStyle &Value) {
574 IO.enumCase(Value, "None", FormatStyle::SFS_None);
575 IO.enumCase(Value, "false", FormatStyle::SFS_None);
576 IO.enumCase(Value, "All", FormatStyle::SFS_All);
577 IO.enumCase(Value, "true", FormatStyle::SFS_All);
578 IO.enumCase(Value, "Inline", FormatStyle::SFS_Inline);
579 IO.enumCase(Value, "InlineOnly", FormatStyle::SFS_InlineOnly);
580 IO.enumCase(Value, "Empty", FormatStyle::SFS_Empty);
581 }
582};
583
584template <> struct ScalarEnumerationTraits<FormatStyle::ShortIfStyle> {
585 static void enumeration(IO &IO, FormatStyle::ShortIfStyle &Value) {
586 IO.enumCase(Value, "Never", FormatStyle::SIS_Never);
587 IO.enumCase(Value, "WithoutElse", FormatStyle::SIS_WithoutElse);
588 IO.enumCase(Value, "OnlyFirstIf", FormatStyle::SIS_OnlyFirstIf);
589 IO.enumCase(Value, "AllIfsAndElse", FormatStyle::SIS_AllIfsAndElse);
590
591 // For backward compatibility.
592 IO.enumCase(Value, "Always", FormatStyle::SIS_OnlyFirstIf);
593 IO.enumCase(Value, "false", FormatStyle::SIS_Never);
594 IO.enumCase(Value, "true", FormatStyle::SIS_WithoutElse);
595 }
596};
597
598template <> struct ScalarEnumerationTraits<FormatStyle::ShortLambdaStyle> {
599 static void enumeration(IO &IO, FormatStyle::ShortLambdaStyle &Value) {
600 IO.enumCase(Value, "None", FormatStyle::SLS_None);
601 IO.enumCase(Value, "false", FormatStyle::SLS_None);
602 IO.enumCase(Value, "Empty", FormatStyle::SLS_Empty);
603 IO.enumCase(Value, "Inline", FormatStyle::SLS_Inline);
604 IO.enumCase(Value, "All", FormatStyle::SLS_All);
605 IO.enumCase(Value, "true", FormatStyle::SLS_All);
606 }
607};
608
609template <> struct ScalarEnumerationTraits<FormatStyle::SortIncludesOptions> {
610 static void enumeration(IO &IO, FormatStyle::SortIncludesOptions &Value) {
611 IO.enumCase(Value, "Never", FormatStyle::SI_Never);
612 IO.enumCase(Value, "CaseInsensitive", FormatStyle::SI_CaseInsensitive);
613 IO.enumCase(Value, "CaseSensitive", FormatStyle::SI_CaseSensitive);
614
615 // For backward compatibility.
616 IO.enumCase(Value, "false", FormatStyle::SI_Never);
617 IO.enumCase(Value, "true", FormatStyle::SI_CaseSensitive);
618 }
619};
620
621template <>
622struct ScalarEnumerationTraits<FormatStyle::SortJavaStaticImportOptions> {
623 static void enumeration(IO &IO,
624 FormatStyle::SortJavaStaticImportOptions &Value) {
625 IO.enumCase(Value, "Before", FormatStyle::SJSIO_Before);
626 IO.enumCase(Value, "After", FormatStyle::SJSIO_After);
627 }
628};
629
630template <>
631struct ScalarEnumerationTraits<FormatStyle::SortUsingDeclarationsOptions> {
632 static void enumeration(IO &IO,
633 FormatStyle::SortUsingDeclarationsOptions &Value) {
634 IO.enumCase(Value, "Never", FormatStyle::SUD_Never);
635 IO.enumCase(Value, "Lexicographic", FormatStyle::SUD_Lexicographic);
636 IO.enumCase(Value, "LexicographicNumeric",
637 FormatStyle::SUD_LexicographicNumeric);
638
639 // For backward compatibility.
640 IO.enumCase(Value, "false", FormatStyle::SUD_Never);
641 IO.enumCase(Value, "true", FormatStyle::SUD_LexicographicNumeric);
642 }
643};
644
645template <>
646struct ScalarEnumerationTraits<FormatStyle::SpaceAroundPointerQualifiersStyle> {
647 static void
648 enumeration(IO &IO, FormatStyle::SpaceAroundPointerQualifiersStyle &Value) {
649 IO.enumCase(Value, "Default", FormatStyle::SAPQ_Default);
650 IO.enumCase(Value, "Before", FormatStyle::SAPQ_Before);
651 IO.enumCase(Value, "After", FormatStyle::SAPQ_After);
652 IO.enumCase(Value, "Both", FormatStyle::SAPQ_Both);
653 }
654};
655
656template <> struct MappingTraits<FormatStyle::SpaceBeforeParensCustom> {
657 static void mapping(IO &IO, FormatStyle::SpaceBeforeParensCustom &Spacing) {
658 IO.mapOptional("AfterControlStatements", Spacing.AfterControlStatements);
659 IO.mapOptional("AfterForeachMacros", Spacing.AfterForeachMacros);
660 IO.mapOptional("AfterFunctionDefinitionName",
661 Spacing.AfterFunctionDefinitionName);
662 IO.mapOptional("AfterFunctionDeclarationName",
663 Spacing.AfterFunctionDeclarationName);
664 IO.mapOptional("AfterIfMacros", Spacing.AfterIfMacros);
665 IO.mapOptional("AfterOverloadedOperator", Spacing.AfterOverloadedOperator);
666 IO.mapOptional("AfterPlacementOperator", Spacing.AfterPlacementOperator);
667 IO.mapOptional("AfterRequiresInClause", Spacing.AfterRequiresInClause);
668 IO.mapOptional("AfterRequiresInExpression",
669 Spacing.AfterRequiresInExpression);
670 IO.mapOptional("BeforeNonEmptyParentheses",
671 Spacing.BeforeNonEmptyParentheses);
672 }
673};
674
675template <>
676struct ScalarEnumerationTraits<FormatStyle::SpaceBeforeParensStyle> {
677 static void enumeration(IO &IO, FormatStyle::SpaceBeforeParensStyle &Value) {
678 IO.enumCase(Value, "Never", FormatStyle::SBPO_Never);
679 IO.enumCase(Value, "ControlStatements",
680 FormatStyle::SBPO_ControlStatements);
681 IO.enumCase(Value, "ControlStatementsExceptControlMacros",
682 FormatStyle::SBPO_ControlStatementsExceptControlMacros);
683 IO.enumCase(Value, "NonEmptyParentheses",
684 FormatStyle::SBPO_NonEmptyParentheses);
685 IO.enumCase(Value, "Always", FormatStyle::SBPO_Always);
686 IO.enumCase(Value, "Custom", FormatStyle::SBPO_Custom);
687
688 // For backward compatibility.
689 IO.enumCase(Value, "false", FormatStyle::SBPO_Never);
690 IO.enumCase(Value, "true", FormatStyle::SBPO_ControlStatements);
691 IO.enumCase(Value, "ControlStatementsExceptForEachMacros",
692 FormatStyle::SBPO_ControlStatementsExceptControlMacros);
693 }
694};
695
696template <> struct ScalarEnumerationTraits<FormatStyle::SpacesInAnglesStyle> {
697 static void enumeration(IO &IO, FormatStyle::SpacesInAnglesStyle &Value) {
698 IO.enumCase(Value, "Never", FormatStyle::SIAS_Never);
699 IO.enumCase(Value, "Always", FormatStyle::SIAS_Always);
700 IO.enumCase(Value, "Leave", FormatStyle::SIAS_Leave);
701
702 // For backward compatibility.
703 IO.enumCase(Value, "false", FormatStyle::SIAS_Never);
704 IO.enumCase(Value, "true", FormatStyle::SIAS_Always);
705 }
706};
707
708template <> struct MappingTraits<FormatStyle::SpacesInLineComment> {
709 static void mapping(IO &IO, FormatStyle::SpacesInLineComment &Space) {
710 // Transform the maximum to signed, to parse "-1" correctly
711 int signedMaximum = static_cast<int>(Space.Maximum);
712 IO.mapOptional("Minimum", Space.Minimum);
713 IO.mapOptional("Maximum", signedMaximum);
714 Space.Maximum = static_cast<unsigned>(signedMaximum);
715
716 if (Space.Maximum != -1u)
717 Space.Minimum = std::min(Space.Minimum, Space.Maximum);
718 }
719};
720
721template <> struct MappingTraits<FormatStyle::SpacesInParensCustom> {
722 static void mapping(IO &IO, FormatStyle::SpacesInParensCustom &Spaces) {
723 IO.mapOptional("InCStyleCasts", Spaces.InCStyleCasts);
724 IO.mapOptional("InConditionalStatements", Spaces.InConditionalStatements);
725 IO.mapOptional("InEmptyParentheses", Spaces.InEmptyParentheses);
726 IO.mapOptional("Other", Spaces.Other);
727 }
728};
729
730template <> struct ScalarEnumerationTraits<FormatStyle::SpacesInParensStyle> {
731 static void enumeration(IO &IO, FormatStyle::SpacesInParensStyle &Value) {
732 IO.enumCase(Value, "Never", FormatStyle::SIPO_Never);
733 IO.enumCase(Value, "Custom", FormatStyle::SIPO_Custom);
734 }
735};
736
737template <> struct ScalarEnumerationTraits<FormatStyle::TrailingCommaStyle> {
738 static void enumeration(IO &IO, FormatStyle::TrailingCommaStyle &Value) {
739 IO.enumCase(Value, "None", FormatStyle::TCS_None);
740 IO.enumCase(Value, "Wrapped", FormatStyle::TCS_Wrapped);
741 }
742};
743
744template <>
745struct ScalarEnumerationTraits<FormatStyle::TrailingCommentsAlignmentKinds> {
746 static void enumeration(IO &IO,
747 FormatStyle::TrailingCommentsAlignmentKinds &Value) {
748 IO.enumCase(Value, "Leave", FormatStyle::TCAS_Leave);
749 IO.enumCase(Value, "Always", FormatStyle::TCAS_Always);
750 IO.enumCase(Value, "Never", FormatStyle::TCAS_Never);
751 }
752};
753
754template <> struct MappingTraits<FormatStyle::TrailingCommentsAlignmentStyle> {
755 static void enumInput(IO &IO,
756 FormatStyle::TrailingCommentsAlignmentStyle &Value) {
757 IO.enumCase(Value, "Leave",
758 FormatStyle::TrailingCommentsAlignmentStyle(
759 {FormatStyle::TCAS_Leave, 0}));
760
761 IO.enumCase(Value, "Always",
762 FormatStyle::TrailingCommentsAlignmentStyle(
763 {FormatStyle::TCAS_Always, 0}));
764
765 IO.enumCase(Value, "Never",
766 FormatStyle::TrailingCommentsAlignmentStyle(
767 {FormatStyle::TCAS_Never, 0}));
768
769 // For backwards compatibility
770 IO.enumCase(Value, "true",
771 FormatStyle::TrailingCommentsAlignmentStyle(
772 {FormatStyle::TCAS_Always, 0}));
773 IO.enumCase(Value, "false",
774 FormatStyle::TrailingCommentsAlignmentStyle(
775 {FormatStyle::TCAS_Never, 0}));
776 }
777
778 static void mapping(IO &IO,
779 FormatStyle::TrailingCommentsAlignmentStyle &Value) {
780 IO.mapOptional("Kind", Value.Kind);
781 IO.mapOptional("OverEmptyLines", Value.OverEmptyLines);
782 }
783};
784
785template <> struct ScalarEnumerationTraits<FormatStyle::UseTabStyle> {
786 static void enumeration(IO &IO, FormatStyle::UseTabStyle &Value) {
787 IO.enumCase(Value, "Never", FormatStyle::UT_Never);
788 IO.enumCase(Value, "false", FormatStyle::UT_Never);
789 IO.enumCase(Value, "Always", FormatStyle::UT_Always);
790 IO.enumCase(Value, "true", FormatStyle::UT_Always);
791 IO.enumCase(Value, "ForIndentation", FormatStyle::UT_ForIndentation);
792 IO.enumCase(Value, "ForContinuationAndIndentation",
793 FormatStyle::UT_ForContinuationAndIndentation);
794 IO.enumCase(Value, "AlignWithSpaces", FormatStyle::UT_AlignWithSpaces);
795 }
796};
797
798template <> struct MappingTraits<FormatStyle> {
799 static void mapping(IO &IO, FormatStyle &Style) {
800 // When reading, read the language first, we need it for getPredefinedStyle.
801 IO.mapOptional("Language", Style.Language);
802
803 StringRef BasedOnStyle;
804 if (IO.outputting()) {
805 StringRef Styles[] = {"LLVM", "Google", "Chromium", "Mozilla",
806 "WebKit", "GNU", "Microsoft", "clang-format"};
807 for (StringRef StyleName : Styles) {
808 FormatStyle PredefinedStyle;
809 if (getPredefinedStyle(StyleName, Style.Language, &PredefinedStyle) &&
810 Style == PredefinedStyle) {
811 BasedOnStyle = StyleName;
812 break;
813 }
814 }
815 } else {
816 IO.mapOptional("BasedOnStyle", BasedOnStyle);
817 if (!BasedOnStyle.empty()) {
818 FormatStyle::LanguageKind OldLanguage = Style.Language;
819 FormatStyle::LanguageKind Language =
820 ((FormatStyle *)IO.getContext())->Language;
821 if (!getPredefinedStyle(BasedOnStyle, Language, &Style)) {
822 IO.setError(Twine("Unknown value for BasedOnStyle: ", BasedOnStyle));
823 return;
824 }
825 Style.Language = OldLanguage;
826 }
827 }
828
829 // Initialize some variables used in the parsing. The using logic is at the
830 // end.
831
832 // For backward compatibility:
833 // The default value of ConstructorInitializerAllOnOneLineOrOnePerLine was
834 // false unless BasedOnStyle was Google or Chromium whereas that of
835 // AllowAllConstructorInitializersOnNextLine was always true, so the
836 // equivalent default value of PackConstructorInitializers is PCIS_NextLine
837 // for Google/Chromium or PCIS_BinPack otherwise. If the deprecated options
838 // had a non-default value while PackConstructorInitializers has a default
839 // value, set the latter to an equivalent non-default value if needed.
840 const bool IsGoogleOrChromium = BasedOnStyle.equals_insensitive("google") ||
841 BasedOnStyle.equals_insensitive("chromium");
842 bool OnCurrentLine = IsGoogleOrChromium;
843 bool OnNextLine = true;
844
845 bool BreakBeforeInheritanceComma = false;
846 bool BreakConstructorInitializersBeforeComma = false;
847
848 bool DeriveLineEnding = true;
849 bool UseCRLF = false;
850
851 bool SpaceInEmptyParentheses = false;
852 bool SpacesInConditionalStatement = false;
853 bool SpacesInCStyleCastParentheses = false;
854 bool SpacesInParentheses = false;
855
856 // For backward compatibility.
857 if (!IO.outputting()) {
858 IO.mapOptional("AlignEscapedNewlinesLeft", Style.AlignEscapedNewlines);
859 IO.mapOptional("AllowAllConstructorInitializersOnNextLine", OnNextLine);
860 IO.mapOptional("AlwaysBreakAfterReturnType", Style.BreakAfterReturnType);
861 IO.mapOptional("AlwaysBreakTemplateDeclarations",
863 IO.mapOptional("BreakBeforeInheritanceComma",
864 BreakBeforeInheritanceComma);
865 IO.mapOptional("BreakConstructorInitializersBeforeComma",
866 BreakConstructorInitializersBeforeComma);
867 IO.mapOptional("ConstructorInitializerAllOnOneLineOrOnePerLine",
868 OnCurrentLine);
869 IO.mapOptional("DeriveLineEnding", DeriveLineEnding);
870 IO.mapOptional("DerivePointerBinding", Style.DerivePointerAlignment);
871 IO.mapOptional("IndentFunctionDeclarationAfterType",
873 IO.mapOptional("IndentRequires", Style.IndentRequiresClause);
874 IO.mapOptional("PointerBindsToType", Style.PointerAlignment);
875 IO.mapOptional("SpaceAfterControlStatementKeyword",
876 Style.SpaceBeforeParens);
877 IO.mapOptional("SpaceInEmptyParentheses", SpaceInEmptyParentheses);
878 IO.mapOptional("SpacesInConditionalStatement",
879 SpacesInConditionalStatement);
880 IO.mapOptional("SpacesInCStyleCastParentheses",
881 SpacesInCStyleCastParentheses);
882 IO.mapOptional("SpacesInParentheses", SpacesInParentheses);
883 IO.mapOptional("UseCRLF", UseCRLF);
884 }
885
886 IO.mapOptional("AccessModifierOffset", Style.AccessModifierOffset);
887 IO.mapOptional("AlignAfterOpenBracket", Style.AlignAfterOpenBracket);
888 IO.mapOptional("AlignArrayOfStructures", Style.AlignArrayOfStructures);
889 IO.mapOptional("AlignConsecutiveAssignments",
891 IO.mapOptional("AlignConsecutiveBitFields",
893 IO.mapOptional("AlignConsecutiveDeclarations",
895 IO.mapOptional("AlignConsecutiveMacros", Style.AlignConsecutiveMacros);
896 IO.mapOptional("AlignConsecutiveShortCaseStatements",
898 IO.mapOptional("AlignConsecutiveTableGenBreakingDAGArgColons",
900 IO.mapOptional("AlignConsecutiveTableGenCondOperatorColons",
902 IO.mapOptional("AlignConsecutiveTableGenDefinitionColons",
904 IO.mapOptional("AlignEscapedNewlines", Style.AlignEscapedNewlines);
905 IO.mapOptional("AlignOperands", Style.AlignOperands);
906 IO.mapOptional("AlignTrailingComments", Style.AlignTrailingComments);
907 IO.mapOptional("AllowAllArgumentsOnNextLine",
909 IO.mapOptional("AllowAllParametersOfDeclarationOnNextLine",
911 IO.mapOptional("AllowBreakBeforeNoexceptSpecifier",
913 IO.mapOptional("AllowShortBlocksOnASingleLine",
915 IO.mapOptional("AllowShortCaseExpressionOnASingleLine",
917 IO.mapOptional("AllowShortCaseLabelsOnASingleLine",
919 IO.mapOptional("AllowShortCompoundRequirementOnASingleLine",
921 IO.mapOptional("AllowShortEnumsOnASingleLine",
923 IO.mapOptional("AllowShortFunctionsOnASingleLine",
925 IO.mapOptional("AllowShortIfStatementsOnASingleLine",
927 IO.mapOptional("AllowShortLambdasOnASingleLine",
929 IO.mapOptional("AllowShortLoopsOnASingleLine",
931 IO.mapOptional("AlwaysBreakAfterDefinitionReturnType",
933 IO.mapOptional("AlwaysBreakBeforeMultilineStrings",
935 IO.mapOptional("AttributeMacros", Style.AttributeMacros);
936 IO.mapOptional("BinPackArguments", Style.BinPackArguments);
937 IO.mapOptional("BinPackParameters", Style.BinPackParameters);
938 IO.mapOptional("BitFieldColonSpacing", Style.BitFieldColonSpacing);
939 IO.mapOptional("BracedInitializerIndentWidth",
941 IO.mapOptional("BraceWrapping", Style.BraceWrapping);
942 IO.mapOptional("BreakAdjacentStringLiterals",
944 IO.mapOptional("BreakAfterAttributes", Style.BreakAfterAttributes);
945 IO.mapOptional("BreakAfterJavaFieldAnnotations",
947 IO.mapOptional("BreakAfterReturnType", Style.BreakAfterReturnType);
948 IO.mapOptional("BreakArrays", Style.BreakArrays);
949 IO.mapOptional("BreakBeforeBinaryOperators",
951 IO.mapOptional("BreakBeforeConceptDeclarations",
953 IO.mapOptional("BreakBeforeBraces", Style.BreakBeforeBraces);
954 IO.mapOptional("BreakBeforeInlineASMColon",
956 IO.mapOptional("BreakBeforeTernaryOperators",
958 IO.mapOptional("BreakConstructorInitializers",
960 IO.mapOptional("BreakFunctionDefinitionParameters",
962 IO.mapOptional("BreakInheritanceList", Style.BreakInheritanceList);
963 IO.mapOptional("BreakStringLiterals", Style.BreakStringLiterals);
964 IO.mapOptional("BreakTemplateDeclarations",
966 IO.mapOptional("ColumnLimit", Style.ColumnLimit);
967 IO.mapOptional("CommentPragmas", Style.CommentPragmas);
968 IO.mapOptional("CompactNamespaces", Style.CompactNamespaces);
969 IO.mapOptional("ConstructorInitializerIndentWidth",
971 IO.mapOptional("ContinuationIndentWidth", Style.ContinuationIndentWidth);
972 IO.mapOptional("Cpp11BracedListStyle", Style.Cpp11BracedListStyle);
973 IO.mapOptional("DerivePointerAlignment", Style.DerivePointerAlignment);
974 IO.mapOptional("DisableFormat", Style.DisableFormat);
975 IO.mapOptional("EmptyLineAfterAccessModifier",
977 IO.mapOptional("EmptyLineBeforeAccessModifier",
979 IO.mapOptional("ExperimentalAutoDetectBinPacking",
981 IO.mapOptional("FixNamespaceComments", Style.FixNamespaceComments);
982 IO.mapOptional("ForEachMacros", Style.ForEachMacros);
983 IO.mapOptional("IfMacros", Style.IfMacros);
984 IO.mapOptional("IncludeBlocks", Style.IncludeStyle.IncludeBlocks);
985 IO.mapOptional("IncludeCategories", Style.IncludeStyle.IncludeCategories);
986 IO.mapOptional("IncludeIsMainRegex", Style.IncludeStyle.IncludeIsMainRegex);
987 IO.mapOptional("IncludeIsMainSourceRegex",
989 IO.mapOptional("IndentAccessModifiers", Style.IndentAccessModifiers);
990 IO.mapOptional("IndentCaseBlocks", Style.IndentCaseBlocks);
991 IO.mapOptional("IndentCaseLabels", Style.IndentCaseLabels);
992 IO.mapOptional("IndentExternBlock", Style.IndentExternBlock);
993 IO.mapOptional("IndentGotoLabels", Style.IndentGotoLabels);
994 IO.mapOptional("IndentPPDirectives", Style.IndentPPDirectives);
995 IO.mapOptional("IndentRequiresClause", Style.IndentRequiresClause);
996 IO.mapOptional("IndentWidth", Style.IndentWidth);
997 IO.mapOptional("IndentWrappedFunctionNames",
999 IO.mapOptional("InsertBraces", Style.InsertBraces);
1000 IO.mapOptional("InsertNewlineAtEOF", Style.InsertNewlineAtEOF);
1001 IO.mapOptional("InsertTrailingCommas", Style.InsertTrailingCommas);
1002 IO.mapOptional("IntegerLiteralSeparator", Style.IntegerLiteralSeparator);
1003 IO.mapOptional("JavaImportGroups", Style.JavaImportGroups);
1004 IO.mapOptional("JavaScriptQuotes", Style.JavaScriptQuotes);
1005 IO.mapOptional("JavaScriptWrapImports", Style.JavaScriptWrapImports);
1006 IO.mapOptional("KeepEmptyLinesAtTheStartOfBlocks",
1008 IO.mapOptional("KeepEmptyLinesAtEOF", Style.KeepEmptyLinesAtEOF);
1009 IO.mapOptional("LambdaBodyIndentation", Style.LambdaBodyIndentation);
1010 IO.mapOptional("LineEnding", Style.LineEnding);
1011 IO.mapOptional("MacroBlockBegin", Style.MacroBlockBegin);
1012 IO.mapOptional("MacroBlockEnd", Style.MacroBlockEnd);
1013 IO.mapOptional("Macros", Style.Macros);
1014 IO.mapOptional("MainIncludeChar", Style.IncludeStyle.MainIncludeChar);
1015 IO.mapOptional("MaxEmptyLinesToKeep", Style.MaxEmptyLinesToKeep);
1016 IO.mapOptional("NamespaceIndentation", Style.NamespaceIndentation);
1017 IO.mapOptional("NamespaceMacros", Style.NamespaceMacros);
1018 IO.mapOptional("ObjCBinPackProtocolList", Style.ObjCBinPackProtocolList);
1019 IO.mapOptional("ObjCBlockIndentWidth", Style.ObjCBlockIndentWidth);
1020 IO.mapOptional("ObjCBreakBeforeNestedBlockParam",
1022 IO.mapOptional("ObjCPropertyAttributeOrder",
1024 IO.mapOptional("ObjCSpaceAfterProperty", Style.ObjCSpaceAfterProperty);
1025 IO.mapOptional("ObjCSpaceBeforeProtocolList",
1027 IO.mapOptional("PackConstructorInitializers",
1029 IO.mapOptional("PenaltyBreakAssignment", Style.PenaltyBreakAssignment);
1030 IO.mapOptional("PenaltyBreakBeforeFirstCallParameter",
1032 IO.mapOptional("PenaltyBreakComment", Style.PenaltyBreakComment);
1033 IO.mapOptional("PenaltyBreakFirstLessLess",
1035 IO.mapOptional("PenaltyBreakOpenParenthesis",
1037 IO.mapOptional("PenaltyBreakScopeResolution",
1039 IO.mapOptional("PenaltyBreakString", Style.PenaltyBreakString);
1040 IO.mapOptional("PenaltyBreakTemplateDeclaration",
1042 IO.mapOptional("PenaltyExcessCharacter", Style.PenaltyExcessCharacter);
1043 IO.mapOptional("PenaltyIndentedWhitespace",
1045 IO.mapOptional("PenaltyReturnTypeOnItsOwnLine",
1047 IO.mapOptional("PointerAlignment", Style.PointerAlignment);
1048 IO.mapOptional("PPIndentWidth", Style.PPIndentWidth);
1049 IO.mapOptional("QualifierAlignment", Style.QualifierAlignment);
1050 // Default Order for Left/Right based Qualifier alignment.
1051 if (Style.QualifierAlignment == FormatStyle::QAS_Right)
1052 Style.QualifierOrder = {"type", "const", "volatile"};
1053 else if (Style.QualifierAlignment == FormatStyle::QAS_Left)
1054 Style.QualifierOrder = {"const", "volatile", "type"};
1055 else if (Style.QualifierAlignment == FormatStyle::QAS_Custom)
1056 IO.mapOptional("QualifierOrder", Style.QualifierOrder);
1057 IO.mapOptional("RawStringFormats", Style.RawStringFormats);
1058 IO.mapOptional("ReferenceAlignment", Style.ReferenceAlignment);
1059 IO.mapOptional("ReflowComments", Style.ReflowComments);
1060 IO.mapOptional("RemoveBracesLLVM", Style.RemoveBracesLLVM);
1061 IO.mapOptional("RemoveParentheses", Style.RemoveParentheses);
1062 IO.mapOptional("RemoveSemicolon", Style.RemoveSemicolon);
1063 IO.mapOptional("RequiresClausePosition", Style.RequiresClausePosition);
1064 IO.mapOptional("RequiresExpressionIndentation",
1066 IO.mapOptional("SeparateDefinitionBlocks", Style.SeparateDefinitionBlocks);
1067 IO.mapOptional("ShortNamespaceLines", Style.ShortNamespaceLines);
1068 IO.mapOptional("SkipMacroDefinitionBody", Style.SkipMacroDefinitionBody);
1069 IO.mapOptional("SortIncludes", Style.SortIncludes);
1070 IO.mapOptional("SortJavaStaticImport", Style.SortJavaStaticImport);
1071 IO.mapOptional("SortUsingDeclarations", Style.SortUsingDeclarations);
1072 IO.mapOptional("SpaceAfterCStyleCast", Style.SpaceAfterCStyleCast);
1073 IO.mapOptional("SpaceAfterLogicalNot", Style.SpaceAfterLogicalNot);
1074 IO.mapOptional("SpaceAfterTemplateKeyword",
1076 IO.mapOptional("SpaceAroundPointerQualifiers",
1078 IO.mapOptional("SpaceBeforeAssignmentOperators",
1080 IO.mapOptional("SpaceBeforeCaseColon", Style.SpaceBeforeCaseColon);
1081 IO.mapOptional("SpaceBeforeCpp11BracedList",
1083 IO.mapOptional("SpaceBeforeCtorInitializerColon",
1085 IO.mapOptional("SpaceBeforeInheritanceColon",
1087 IO.mapOptional("SpaceBeforeJsonColon", Style.SpaceBeforeJsonColon);
1088 IO.mapOptional("SpaceBeforeParens", Style.SpaceBeforeParens);
1089 IO.mapOptional("SpaceBeforeParensOptions", Style.SpaceBeforeParensOptions);
1090 IO.mapOptional("SpaceBeforeRangeBasedForLoopColon",
1092 IO.mapOptional("SpaceBeforeSquareBrackets",
1094 IO.mapOptional("SpaceInEmptyBlock", Style.SpaceInEmptyBlock);
1095 IO.mapOptional("SpacesBeforeTrailingComments",
1097 IO.mapOptional("SpacesInAngles", Style.SpacesInAngles);
1098 IO.mapOptional("SpacesInContainerLiterals",
1100 IO.mapOptional("SpacesInLineCommentPrefix",
1102 IO.mapOptional("SpacesInParens", Style.SpacesInParens);
1103 IO.mapOptional("SpacesInParensOptions", Style.SpacesInParensOptions);
1104 IO.mapOptional("SpacesInSquareBrackets", Style.SpacesInSquareBrackets);
1105 IO.mapOptional("Standard", Style.Standard);
1106 IO.mapOptional("StatementAttributeLikeMacros",
1108 IO.mapOptional("StatementMacros", Style.StatementMacros);
1109 IO.mapOptional("TableGenBreakingDAGArgOperators",
1111 IO.mapOptional("TableGenBreakInsideDAGArg",
1113 IO.mapOptional("TabWidth", Style.TabWidth);
1114 IO.mapOptional("TypeNames", Style.TypeNames);
1115 IO.mapOptional("TypenameMacros", Style.TypenameMacros);
1116 IO.mapOptional("UseTab", Style.UseTab);
1117 IO.mapOptional("VerilogBreakBetweenInstancePorts",
1119 IO.mapOptional("WhitespaceSensitiveMacros",
1121
1122 // If AlwaysBreakAfterDefinitionReturnType was specified but
1123 // BreakAfterReturnType was not, initialize the latter from the former for
1124 // backwards compatibility.
1125 if (Style.AlwaysBreakAfterDefinitionReturnType != FormatStyle::DRTBS_None &&
1126 Style.BreakAfterReturnType == FormatStyle::RTBS_None) {
1128 FormatStyle::DRTBS_All) {
1129 Style.BreakAfterReturnType = FormatStyle::RTBS_AllDefinitions;
1130 } else if (Style.AlwaysBreakAfterDefinitionReturnType ==
1131 FormatStyle::DRTBS_TopLevel) {
1132 Style.BreakAfterReturnType = FormatStyle::RTBS_TopLevelDefinitions;
1133 }
1134 }
1135
1136 // If BreakBeforeInheritanceComma was specified but BreakInheritance was
1137 // not, initialize the latter from the former for backwards compatibility.
1138 if (BreakBeforeInheritanceComma &&
1139 Style.BreakInheritanceList == FormatStyle::BILS_BeforeColon) {
1140 Style.BreakInheritanceList = FormatStyle::BILS_BeforeComma;
1141 }
1142
1143 // If BreakConstructorInitializersBeforeComma was specified but
1144 // BreakConstructorInitializers was not, initialize the latter from the
1145 // former for backwards compatibility.
1146 if (BreakConstructorInitializersBeforeComma &&
1147 Style.BreakConstructorInitializers == FormatStyle::BCIS_BeforeColon) {
1148 Style.BreakConstructorInitializers = FormatStyle::BCIS_BeforeComma;
1149 }
1150
1151 if (!IsGoogleOrChromium) {
1152 if (Style.PackConstructorInitializers == FormatStyle::PCIS_BinPack &&
1153 OnCurrentLine) {
1154 Style.PackConstructorInitializers = OnNextLine
1155 ? FormatStyle::PCIS_NextLine
1156 : FormatStyle::PCIS_CurrentLine;
1157 }
1158 } else if (Style.PackConstructorInitializers ==
1159 FormatStyle::PCIS_NextLine) {
1160 if (!OnCurrentLine)
1161 Style.PackConstructorInitializers = FormatStyle::PCIS_BinPack;
1162 else if (!OnNextLine)
1163 Style.PackConstructorInitializers = FormatStyle::PCIS_CurrentLine;
1164 }
1165
1166 if (Style.LineEnding == FormatStyle::LE_DeriveLF) {
1167 if (!DeriveLineEnding)
1168 Style.LineEnding = UseCRLF ? FormatStyle::LE_CRLF : FormatStyle::LE_LF;
1169 else if (UseCRLF)
1170 Style.LineEnding = FormatStyle::LE_DeriveCRLF;
1171 }
1172
1173 if (Style.SpacesInParens != FormatStyle::SIPO_Custom &&
1174 (SpacesInParentheses || SpaceInEmptyParentheses ||
1175 SpacesInConditionalStatement || SpacesInCStyleCastParentheses)) {
1176 if (SpacesInParentheses) {
1177 // set all options except InCStyleCasts and InEmptyParentheses
1178 // to true for backward compatibility.
1181 SpacesInCStyleCastParentheses;
1183 SpaceInEmptyParentheses;
1184 Style.SpacesInParensOptions.Other = true;
1185 } else {
1186 Style.SpacesInParensOptions = {};
1188 SpacesInConditionalStatement;
1190 SpacesInCStyleCastParentheses;
1192 SpaceInEmptyParentheses;
1193 }
1194 Style.SpacesInParens = FormatStyle::SIPO_Custom;
1195 }
1196 }
1197};
1198
1199// Allows to read vector<FormatStyle> while keeping default values.
1200// IO.getContext() should contain a pointer to the FormatStyle structure, that
1201// will be used to get default values for missing keys.
1202// If the first element has no Language specified, it will be treated as the
1203// default one for the following elements.
1204template <> struct DocumentListTraits<std::vector<FormatStyle>> {
1205 static size_t size(IO &IO, std::vector<FormatStyle> &Seq) {
1206 return Seq.size();
1207 }
1208 static FormatStyle &element(IO &IO, std::vector<FormatStyle> &Seq,
1209 size_t Index) {
1210 if (Index >= Seq.size()) {
1211 assert(Index == Seq.size());
1212 FormatStyle Template;
1213 if (!Seq.empty() && Seq[0].Language == FormatStyle::LK_None) {
1214 Template = Seq[0];
1215 } else {
1216 Template = *((const FormatStyle *)IO.getContext());
1217 Template.Language = FormatStyle::LK_None;
1218 }
1219 Seq.resize(Index + 1, Template);
1220 }
1221 return Seq[Index];
1222 }
1223};
1224} // namespace yaml
1225} // namespace llvm
1226
1227namespace clang {
1228namespace format {
1229
1230const std::error_category &getParseCategory() {
1231 static const ParseErrorCategory C{};
1232 return C;
1233}
1234std::error_code make_error_code(ParseError e) {
1235 return std::error_code(static_cast<int>(e), getParseCategory());
1236}
1237
1238inline llvm::Error make_string_error(const llvm::Twine &Message) {
1239 return llvm::make_error<llvm::StringError>(Message,
1240 llvm::inconvertibleErrorCode());
1241}
1242
1243const char *ParseErrorCategory::name() const noexcept {
1244 return "clang-format.parse_error";
1245}
1246
1247std::string ParseErrorCategory::message(int EV) const {
1248 switch (static_cast<ParseError>(EV)) {
1250 return "Success";
1251 case ParseError::Error:
1252 return "Invalid argument";
1254 return "Unsuitable";
1256 return "trailing comma insertion cannot be used with bin packing";
1258 return "Invalid qualifier specified in QualifierOrder";
1260 return "Duplicate qualifier specified in QualifierOrder";
1262 return "Missing type in QualifierOrder";
1264 return "Missing QualifierOrder";
1265 }
1266 llvm_unreachable("unexpected parse error");
1267}
1268
1271 return;
1272 Expanded.BraceWrapping = {/*AfterCaseLabel=*/false,
1273 /*AfterClass=*/false,
1274 /*AfterControlStatement=*/FormatStyle::BWACS_Never,
1275 /*AfterEnum=*/false,
1276 /*AfterFunction=*/false,
1277 /*AfterNamespace=*/false,
1278 /*AfterObjCDeclaration=*/false,
1279 /*AfterStruct=*/false,
1280 /*AfterUnion=*/false,
1281 /*AfterExternBlock=*/false,
1282 /*BeforeCatch=*/false,
1283 /*BeforeElse=*/false,
1284 /*BeforeLambdaBody=*/false,
1285 /*BeforeWhile=*/false,
1286 /*IndentBraces=*/false,
1287 /*SplitEmptyFunction=*/true,
1288 /*SplitEmptyRecord=*/true,
1289 /*SplitEmptyNamespace=*/true};
1290 switch (Expanded.BreakBeforeBraces) {
1292 Expanded.BraceWrapping.AfterClass = true;
1293 Expanded.BraceWrapping.AfterFunction = true;
1294 Expanded.BraceWrapping.AfterNamespace = true;
1295 break;
1297 Expanded.BraceWrapping.AfterClass = true;
1298 Expanded.BraceWrapping.AfterEnum = true;
1299 Expanded.BraceWrapping.AfterFunction = true;
1300 Expanded.BraceWrapping.AfterStruct = true;
1301 Expanded.BraceWrapping.AfterUnion = true;
1302 Expanded.BraceWrapping.AfterExternBlock = true;
1303 Expanded.BraceWrapping.SplitEmptyFunction = true;
1304 Expanded.BraceWrapping.SplitEmptyRecord = false;
1305 break;
1307 Expanded.BraceWrapping.AfterFunction = true;
1308 Expanded.BraceWrapping.BeforeCatch = true;
1309 Expanded.BraceWrapping.BeforeElse = true;
1310 break;
1312 Expanded.BraceWrapping.AfterCaseLabel = true;
1313 Expanded.BraceWrapping.AfterClass = true;
1315 Expanded.BraceWrapping.AfterEnum = true;
1316 Expanded.BraceWrapping.AfterFunction = true;
1317 Expanded.BraceWrapping.AfterNamespace = true;
1318 Expanded.BraceWrapping.AfterObjCDeclaration = true;
1319 Expanded.BraceWrapping.AfterStruct = true;
1320 Expanded.BraceWrapping.AfterUnion = true;
1321 Expanded.BraceWrapping.AfterExternBlock = true;
1322 Expanded.BraceWrapping.BeforeCatch = true;
1323 Expanded.BraceWrapping.BeforeElse = true;
1324 Expanded.BraceWrapping.BeforeLambdaBody = true;
1325 break;
1327 Expanded.BraceWrapping.AfterCaseLabel = true;
1328 Expanded.BraceWrapping.AfterClass = true;
1330 Expanded.BraceWrapping.AfterEnum = true;
1331 Expanded.BraceWrapping.AfterFunction = true;
1332 Expanded.BraceWrapping.AfterNamespace = true;
1333 Expanded.BraceWrapping.AfterObjCDeclaration = true;
1334 Expanded.BraceWrapping.AfterStruct = true;
1335 Expanded.BraceWrapping.AfterExternBlock = true;
1336 Expanded.BraceWrapping.BeforeCatch = true;
1337 Expanded.BraceWrapping.BeforeElse = true;
1338 Expanded.BraceWrapping.BeforeLambdaBody = true;
1339 break;
1341 Expanded.BraceWrapping = {
1342 /*AfterCaseLabel=*/true,
1343 /*AfterClass=*/true,
1344 /*AfterControlStatement=*/FormatStyle::BWACS_Always,
1345 /*AfterEnum=*/true,
1346 /*AfterFunction=*/true,
1347 /*AfterNamespace=*/true,
1348 /*AfterObjCDeclaration=*/true,
1349 /*AfterStruct=*/true,
1350 /*AfterUnion=*/true,
1351 /*AfterExternBlock=*/true,
1352 /*BeforeCatch=*/true,
1353 /*BeforeElse=*/true,
1354 /*BeforeLambdaBody=*/false,
1355 /*BeforeWhile=*/true,
1356 /*IndentBraces=*/true,
1357 /*SplitEmptyFunction=*/true,
1358 /*SplitEmptyRecord=*/true,
1359 /*SplitEmptyNamespace=*/true};
1360 break;
1362 Expanded.BraceWrapping.AfterFunction = true;
1363 break;
1364 default:
1365 break;
1366 }
1367}
1368
1371 return;
1372 // Reset all flags
1373 Expanded.SpaceBeforeParensOptions = {};
1375
1376 switch (Expanded.SpaceBeforeParens) {
1381 break;
1384 break;
1387 break;
1388 default:
1389 break;
1390 }
1391}
1392
1395 return;
1396 assert(Expanded.SpacesInParens == FormatStyle::SIPO_Never);
1397 // Reset all flags
1398 Expanded.SpacesInParensOptions = {};
1399}
1400
1402 FormatStyle LLVMStyle;
1403 LLVMStyle.AccessModifierOffset = -2;
1406 LLVMStyle.AlignConsecutiveAssignments = {};
1411 LLVMStyle.AlignConsecutiveAssignments.Enabled = false;
1413 LLVMStyle.AlignConsecutiveBitFields = {};
1414 LLVMStyle.AlignConsecutiveDeclarations = {};
1415 LLVMStyle.AlignConsecutiveMacros = {};
1422 LLVMStyle.AlignTrailingComments = {};
1425 LLVMStyle.AllowAllArgumentsOnNextLine = true;
1430 LLVMStyle.AllowShortCaseLabelsOnASingleLine = false;
1432 LLVMStyle.AllowShortEnumsOnASingleLine = true;
1436 LLVMStyle.AllowShortLoopsOnASingleLine = false;
1438 LLVMStyle.AlwaysBreakBeforeMultilineStrings = false;
1439 LLVMStyle.AttributeMacros.push_back("__capability");
1440 LLVMStyle.BinPackArguments = true;
1441 LLVMStyle.BinPackParameters = true;
1443 LLVMStyle.BracedInitializerIndentWidth = std::nullopt;
1444 LLVMStyle.BraceWrapping = {/*AfterCaseLabel=*/false,
1445 /*AfterClass=*/false,
1446 /*AfterControlStatement=*/FormatStyle::BWACS_Never,
1447 /*AfterEnum=*/false,
1448 /*AfterFunction=*/false,
1449 /*AfterNamespace=*/false,
1450 /*AfterObjCDeclaration=*/false,
1451 /*AfterStruct=*/false,
1452 /*AfterUnion=*/false,
1453 /*AfterExternBlock=*/false,
1454 /*BeforeCatch=*/false,
1455 /*BeforeElse=*/false,
1456 /*BeforeLambdaBody=*/false,
1457 /*BeforeWhile=*/false,
1458 /*IndentBraces=*/false,
1459 /*SplitEmptyFunction=*/true,
1460 /*SplitEmptyRecord=*/true,
1461 /*SplitEmptyNamespace=*/true};
1462 LLVMStyle.BreakAdjacentStringLiterals = true;
1464 LLVMStyle.BreakAfterJavaFieldAnnotations = false;
1466 LLVMStyle.BreakArrays = true;
1471 LLVMStyle.BreakBeforeTernaryOperators = true;
1473 LLVMStyle.BreakFunctionDefinitionParameters = false;
1475 LLVMStyle.BreakStringLiterals = true;
1477 LLVMStyle.ColumnLimit = 80;
1478 LLVMStyle.CommentPragmas = "^ IWYU pragma:";
1479 LLVMStyle.CompactNamespaces = false;
1481 LLVMStyle.ContinuationIndentWidth = 4;
1482 LLVMStyle.Cpp11BracedListStyle = true;
1483 LLVMStyle.DerivePointerAlignment = false;
1484 LLVMStyle.DisableFormat = false;
1487 LLVMStyle.ExperimentalAutoDetectBinPacking = false;
1488 LLVMStyle.FixNamespaceComments = true;
1489 LLVMStyle.ForEachMacros.push_back("foreach");
1490 LLVMStyle.ForEachMacros.push_back("Q_FOREACH");
1491 LLVMStyle.ForEachMacros.push_back("BOOST_FOREACH");
1492 LLVMStyle.IfMacros.push_back("KJ_IF_MAYBE");
1494 LLVMStyle.IncludeStyle.IncludeCategories = {
1495 {"^\"(llvm|llvm-c|clang|clang-c)/", 2, 0, false},
1496 {"^(<|\"(gtest|gmock|isl|json)/)", 3, 0, false},
1497 {".*", 1, 0, false}};
1498 LLVMStyle.IncludeStyle.IncludeIsMainRegex = "(Test)?$";
1500 LLVMStyle.IndentAccessModifiers = false;
1501 LLVMStyle.IndentCaseBlocks = false;
1502 LLVMStyle.IndentCaseLabels = false;
1504 LLVMStyle.IndentGotoLabels = true;
1506 LLVMStyle.IndentRequiresClause = true;
1507 LLVMStyle.IndentWidth = 2;
1508 LLVMStyle.IndentWrappedFunctionNames = false;
1509 LLVMStyle.InheritsParentConfig = false;
1510 LLVMStyle.InsertBraces = false;
1511 LLVMStyle.InsertNewlineAtEOF = false;
1513 LLVMStyle.IntegerLiteralSeparator = {
1514 /*Binary=*/0, /*BinaryMinDigits=*/0,
1515 /*Decimal=*/0, /*DecimalMinDigits=*/0,
1516 /*Hex=*/0, /*HexMinDigits=*/0};
1518 LLVMStyle.JavaScriptWrapImports = true;
1519 LLVMStyle.KeepEmptyLinesAtEOF = false;
1520 LLVMStyle.KeepEmptyLinesAtTheStartOfBlocks = true;
1522 LLVMStyle.Language = Language;
1524 LLVMStyle.MaxEmptyLinesToKeep = 1;
1527 LLVMStyle.ObjCBlockIndentWidth = 2;
1528 LLVMStyle.ObjCBreakBeforeNestedBlockParam = true;
1529 LLVMStyle.ObjCSpaceAfterProperty = false;
1530 LLVMStyle.ObjCSpaceBeforeProtocolList = true;
1533 LLVMStyle.PPIndentWidth = -1;
1536 LLVMStyle.ReflowComments = true;
1537 LLVMStyle.RemoveBracesLLVM = false;
1539 LLVMStyle.RemoveSemicolon = false;
1543 LLVMStyle.ShortNamespaceLines = 1;
1544 LLVMStyle.SkipMacroDefinitionBody = false;
1548 LLVMStyle.SpaceAfterCStyleCast = false;
1549 LLVMStyle.SpaceAfterLogicalNot = false;
1550 LLVMStyle.SpaceAfterTemplateKeyword = true;
1552 LLVMStyle.SpaceBeforeAssignmentOperators = true;
1553 LLVMStyle.SpaceBeforeCaseColon = false;
1554 LLVMStyle.SpaceBeforeCpp11BracedList = false;
1555 LLVMStyle.SpaceBeforeCtorInitializerColon = true;
1556 LLVMStyle.SpaceBeforeInheritanceColon = true;
1557 LLVMStyle.SpaceBeforeJsonColon = false;
1559 LLVMStyle.SpaceBeforeParensOptions = {};
1562 LLVMStyle.SpaceBeforeParensOptions.AfterIfMacros = true;
1563 LLVMStyle.SpaceBeforeRangeBasedForLoopColon = true;
1564 LLVMStyle.SpaceBeforeSquareBrackets = false;
1565 LLVMStyle.SpaceInEmptyBlock = false;
1566 LLVMStyle.SpacesBeforeTrailingComments = 1;
1568 LLVMStyle.SpacesInContainerLiterals = true;
1569 LLVMStyle.SpacesInLineCommentPrefix = {/*Minimum=*/1, /*Maximum=*/-1u};
1571 LLVMStyle.SpacesInSquareBrackets = false;
1572 LLVMStyle.Standard = FormatStyle::LS_Latest;
1573 LLVMStyle.StatementAttributeLikeMacros.push_back("Q_EMIT");
1574 LLVMStyle.StatementMacros.push_back("Q_UNUSED");
1575 LLVMStyle.StatementMacros.push_back("QT_REQUIRE_VERSION");
1576 LLVMStyle.TableGenBreakingDAGArgOperators = {};
1578 LLVMStyle.TabWidth = 8;
1579 LLVMStyle.UseTab = FormatStyle::UT_Never;
1580 LLVMStyle.VerilogBreakBetweenInstancePorts = true;
1581 LLVMStyle.WhitespaceSensitiveMacros.push_back("BOOST_PP_STRINGIZE");
1582 LLVMStyle.WhitespaceSensitiveMacros.push_back("CF_SWIFT_NAME");
1583 LLVMStyle.WhitespaceSensitiveMacros.push_back("NS_SWIFT_NAME");
1584 LLVMStyle.WhitespaceSensitiveMacros.push_back("PP_STRINGIZE");
1585 LLVMStyle.WhitespaceSensitiveMacros.push_back("STRINGIZE");
1586
1589 LLVMStyle.PenaltyBreakComment = 300;
1590 LLVMStyle.PenaltyBreakFirstLessLess = 120;
1591 LLVMStyle.PenaltyBreakOpenParenthesis = 0;
1592 LLVMStyle.PenaltyBreakScopeResolution = 500;
1593 LLVMStyle.PenaltyBreakString = 1000;
1595 LLVMStyle.PenaltyExcessCharacter = 1'000'000;
1596 LLVMStyle.PenaltyIndentedWhitespace = 0;
1597 LLVMStyle.PenaltyReturnTypeOnItsOwnLine = 60;
1598
1599 // Defaults that differ when not C++.
1600 switch (Language) {
1602 LLVMStyle.SpacesInContainerLiterals = false;
1603 break;
1605 LLVMStyle.ColumnLimit = 0;
1606 break;
1608 LLVMStyle.IndentCaseLabels = true;
1609 LLVMStyle.SpacesInContainerLiterals = false;
1610 break;
1611 default:
1612 break;
1613 }
1614
1615 return LLVMStyle;
1616}
1617
1621 GoogleStyle.Language = FormatStyle::LK_TextProto;
1622
1623 return GoogleStyle;
1624 }
1625
1626 FormatStyle GoogleStyle = getLLVMStyle(Language);
1627
1628 GoogleStyle.AccessModifierOffset = -1;
1632 GoogleStyle.AllowShortLoopsOnASingleLine = true;
1633 GoogleStyle.AlwaysBreakBeforeMultilineStrings = true;
1635 GoogleStyle.DerivePointerAlignment = true;
1637 GoogleStyle.IncludeStyle.IncludeCategories = {{"^<ext/.*\\.h>", 2, 0, false},
1638 {"^<.*\\.h>", 1, 0, false},
1639 {"^<.*", 2, 0, false},
1640 {".*", 3, 0, false}};
1641 GoogleStyle.IncludeStyle.IncludeIsMainRegex = "([-_](test|unittest))?$";
1642 GoogleStyle.IndentCaseLabels = true;
1643 GoogleStyle.KeepEmptyLinesAtTheStartOfBlocks = false;
1645 GoogleStyle.ObjCSpaceAfterProperty = false;
1646 GoogleStyle.ObjCSpaceBeforeProtocolList = true;
1649 GoogleStyle.RawStringFormats = {
1650 {
1652 /*Delimiters=*/
1653 {
1654 "cc",
1655 "CC",
1656 "cpp",
1657 "Cpp",
1658 "CPP",
1659 "c++",
1660 "C++",
1661 },
1662 /*EnclosingFunctionNames=*/
1663 {},
1664 /*CanonicalDelimiter=*/"",
1665 /*BasedOnStyle=*/"google",
1666 },
1667 {
1669 /*Delimiters=*/
1670 {
1671 "pb",
1672 "PB",
1673 "proto",
1674 "PROTO",
1675 },
1676 /*EnclosingFunctionNames=*/
1677 {
1678 "EqualsProto",
1679 "EquivToProto",
1680 "PARSE_PARTIAL_TEXT_PROTO",
1681 "PARSE_TEST_PROTO",
1682 "PARSE_TEXT_PROTO",
1683 "ParseTextOrDie",
1684 "ParseTextProtoOrDie",
1685 "ParseTestProto",
1686 "ParsePartialTestProto",
1687 },
1688 /*CanonicalDelimiter=*/"pb",
1689 /*BasedOnStyle=*/"google",
1690 },
1691 };
1692
1693 GoogleStyle.SpacesBeforeTrailingComments = 2;
1694 GoogleStyle.Standard = FormatStyle::LS_Auto;
1695
1697 GoogleStyle.PenaltyReturnTypeOnItsOwnLine = 200;
1698
1702 GoogleStyle.AlignTrailingComments = {};
1706 GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
1708 GoogleStyle.ColumnLimit = 100;
1709 GoogleStyle.SpaceAfterCStyleCast = true;
1710 GoogleStyle.SpacesBeforeTrailingComments = 1;
1711 } else if (Language == FormatStyle::LK_JavaScript) {
1715 // TODO: still under discussion whether to switch to SLS_All.
1717 GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
1718 GoogleStyle.BreakBeforeTernaryOperators = false;
1719 // taze:, triple slash directives (`/// <...`), tslint:, and @see, which is
1720 // commonly followed by overlong URLs.
1721 GoogleStyle.CommentPragmas = "(taze:|^/[ \t]*<|tslint:|@see)";
1722 // TODO: enable once decided, in particular re disabling bin packing.
1723 // https://google.github.io/styleguide/jsguide.html#features-arrays-trailing-comma
1724 // GoogleStyle.InsertTrailingCommas = FormatStyle::TCS_Wrapped;
1726 GoogleStyle.JavaScriptWrapImports = false;
1727 GoogleStyle.MaxEmptyLinesToKeep = 3;
1729 GoogleStyle.SpacesInContainerLiterals = false;
1730 } else if (Language == FormatStyle::LK_Proto) {
1732 GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
1733 // This affects protocol buffer options specifications and text protos.
1734 // Text protos are currently mostly formatted inside C++ raw string literals
1735 // and often the current breaking behavior of string literals is not
1736 // beneficial there. Investigate turning this on once proper string reflow
1737 // has been implemented.
1738 GoogleStyle.BreakStringLiterals = false;
1739 GoogleStyle.Cpp11BracedListStyle = false;
1740 GoogleStyle.SpacesInContainerLiterals = false;
1741 } else if (Language == FormatStyle::LK_ObjC) {
1742 GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
1743 GoogleStyle.ColumnLimit = 100;
1744 // "Regroup" doesn't work well for ObjC yet (main header heuristic,
1745 // relationship between ObjC standard library headers and other heades,
1746 // #imports, etc.)
1747 GoogleStyle.IncludeStyle.IncludeBlocks =
1749 } else if (Language == FormatStyle::LK_CSharp) {
1752 GoogleStyle.BreakStringLiterals = false;
1753 GoogleStyle.ColumnLimit = 100;
1755 }
1756
1757 return GoogleStyle;
1758}
1759
1761 FormatStyle ChromiumStyle = getGoogleStyle(Language);
1762
1763 // Disable include reordering across blocks in Chromium code.
1764 // - clang-format tries to detect that foo.h is the "main" header for
1765 // foo.cc and foo_unittest.cc via IncludeIsMainRegex. However, Chromium
1766 // uses many other suffices (_win.cc, _mac.mm, _posix.cc, _browsertest.cc,
1767 // _private.cc, _impl.cc etc) in different permutations
1768 // (_win_browsertest.cc) so disable this until IncludeIsMainRegex has a
1769 // better default for Chromium code.
1770 // - The default for .cc and .mm files is different (r357695) for Google style
1771 // for the same reason. The plan is to unify this again once the main
1772 // header detection works for Google's ObjC code, but this hasn't happened
1773 // yet. Since Chromium has some ObjC code, switching Chromium is blocked
1774 // on that.
1775 // - Finally, "If include reordering is harmful, put things in different
1776 // blocks to prevent it" has been a recommendation for a long time that
1777 // people are used to. We'll need a dev education push to change this to
1778 // "If include reordering is harmful, put things in a different block and
1779 // _prepend that with a comment_ to prevent it" before changing behavior.
1780 ChromiumStyle.IncludeStyle.IncludeBlocks =
1782
1786 ChromiumStyle.BreakAfterJavaFieldAnnotations = true;
1787 ChromiumStyle.ContinuationIndentWidth = 8;
1788 ChromiumStyle.IndentWidth = 4;
1789 // See styleguide for import groups:
1790 // https://chromium.googlesource.com/chromium/src/+/refs/heads/main/styleguide/java/java.md#Import-Order
1791 ChromiumStyle.JavaImportGroups = {
1792 "android",
1793 "androidx",
1794 "com",
1795 "dalvik",
1796 "junit",
1797 "org",
1798 "com.google.android.apps.chrome",
1799 "org.chromium",
1800 "java",
1801 "javax",
1802 };
1804 } else if (Language == FormatStyle::LK_JavaScript) {
1806 ChromiumStyle.AllowShortLoopsOnASingleLine = false;
1807 } else {
1808 ChromiumStyle.AllowAllParametersOfDeclarationOnNextLine = false;
1811 ChromiumStyle.AllowShortLoopsOnASingleLine = false;
1812 ChromiumStyle.BinPackParameters = false;
1813 ChromiumStyle.DerivePointerAlignment = false;
1815 ChromiumStyle.ColumnLimit = 80;
1816 }
1817 return ChromiumStyle;
1818}
1819
1821 FormatStyle MozillaStyle = getLLVMStyle();
1822 MozillaStyle.AllowAllParametersOfDeclarationOnNextLine = false;
1826 MozillaStyle.BinPackArguments = false;
1827 MozillaStyle.BinPackParameters = false;
1833 MozillaStyle.ConstructorInitializerIndentWidth = 2;
1834 MozillaStyle.ContinuationIndentWidth = 2;
1835 MozillaStyle.Cpp11BracedListStyle = false;
1836 MozillaStyle.FixNamespaceComments = false;
1837 MozillaStyle.IndentCaseLabels = true;
1838 MozillaStyle.ObjCSpaceAfterProperty = true;
1839 MozillaStyle.ObjCSpaceBeforeProtocolList = false;
1840 MozillaStyle.PenaltyReturnTypeOnItsOwnLine = 200;
1842 MozillaStyle.SpaceAfterTemplateKeyword = false;
1843 return MozillaStyle;
1844}
1845
1847 FormatStyle Style = getLLVMStyle();
1848 Style.AccessModifierOffset = -4;
1851 Style.AlignTrailingComments = {};
1857 Style.ColumnLimit = 0;
1858 Style.Cpp11BracedListStyle = false;
1859 Style.FixNamespaceComments = false;
1860 Style.IndentWidth = 4;
1862 Style.ObjCBlockIndentWidth = 4;
1863 Style.ObjCSpaceAfterProperty = true;
1865 Style.SpaceBeforeCpp11BracedList = true;
1866 Style.SpaceInEmptyBlock = true;
1867 return Style;
1868}
1869
1871 FormatStyle Style = getLLVMStyle();
1876 Style.BreakBeforeTernaryOperators = true;
1877 Style.ColumnLimit = 79;
1878 Style.Cpp11BracedListStyle = false;
1879 Style.FixNamespaceComments = false;
1882 return Style;
1883}
1884
1887 Style.ColumnLimit = 120;
1888 Style.TabWidth = 4;
1889 Style.IndentWidth = 4;
1892 Style.BraceWrapping.AfterClass = true;
1894 Style.BraceWrapping.AfterEnum = true;
1895 Style.BraceWrapping.AfterFunction = true;
1896 Style.BraceWrapping.AfterNamespace = true;
1898 Style.BraceWrapping.AfterStruct = true;
1899 Style.BraceWrapping.AfterExternBlock = true;
1900 Style.BraceWrapping.BeforeCatch = true;
1901 Style.BraceWrapping.BeforeElse = true;
1902 Style.BraceWrapping.BeforeWhile = false;
1903 Style.PenaltyReturnTypeOnItsOwnLine = 1000;
1904 Style.AllowShortEnumsOnASingleLine = false;
1908 Style.AllowShortLoopsOnASingleLine = false;
1911 return Style;
1912}
1913
1915 FormatStyle Style = getLLVMStyle();
1916 Style.InsertBraces = true;
1917 Style.InsertNewlineAtEOF = true;
1921 Style.RemoveBracesLLVM = true;
1923 Style.RemoveSemicolon = true;
1924 return Style;
1925}
1926
1928 FormatStyle NoStyle = getLLVMStyle();
1929 NoStyle.DisableFormat = true;
1932 return NoStyle;
1933}
1934
1936 FormatStyle *Style) {
1937 if (Name.equals_insensitive("llvm"))
1938 *Style = getLLVMStyle(Language);
1939 else if (Name.equals_insensitive("chromium"))
1940 *Style = getChromiumStyle(Language);
1941 else if (Name.equals_insensitive("mozilla"))
1942 *Style = getMozillaStyle();
1943 else if (Name.equals_insensitive("google"))
1944 *Style = getGoogleStyle(Language);
1945 else if (Name.equals_insensitive("webkit"))
1946 *Style = getWebKitStyle();
1947 else if (Name.equals_insensitive("gnu"))
1948 *Style = getGNUStyle();
1949 else if (Name.equals_insensitive("microsoft"))
1950 *Style = getMicrosoftStyle(Language);
1951 else if (Name.equals_insensitive("clang-format"))
1952 *Style = getClangFormatStyle();
1953 else if (Name.equals_insensitive("none"))
1954 *Style = getNoStyle();
1955 else if (Name.equals_insensitive("inheritparentconfig"))
1956 Style->InheritsParentConfig = true;
1957 else
1958 return false;
1959
1960 Style->Language = Language;
1961 return true;
1962}
1963
1965 // If its empty then it means don't do anything.
1966 if (Style->QualifierOrder.empty())
1968
1969 // Ensure the list contains only currently valid qualifiers.
1970 for (const auto &Qualifier : Style->QualifierOrder) {
1971 if (Qualifier == "type")
1972 continue;
1973 auto token =
1975 if (token == tok::identifier)
1977 }
1978
1979 // Ensure the list is unique (no duplicates).
1980 std::set<std::string> UniqueQualifiers(Style->QualifierOrder.begin(),
1981 Style->QualifierOrder.end());
1982 if (Style->QualifierOrder.size() != UniqueQualifiers.size()) {
1983 LLVM_DEBUG(llvm::dbgs()
1984 << "Duplicate Qualifiers " << Style->QualifierOrder.size()
1985 << " vs " << UniqueQualifiers.size() << "\n");
1987 }
1988
1989 // Ensure the list has 'type' in it.
1990 if (!llvm::is_contained(Style->QualifierOrder, "type"))
1992
1993 return ParseError::Success;
1994}
1995
1996std::error_code parseConfiguration(llvm::MemoryBufferRef Config,
1997 FormatStyle *Style, bool AllowUnknownOptions,
1998 llvm::SourceMgr::DiagHandlerTy DiagHandler,
1999 void *DiagHandlerCtxt) {
2000 assert(Style);
2002 assert(Language != FormatStyle::LK_None);
2003 if (Config.getBuffer().trim().empty())
2005 Style->StyleSet.Clear();
2006 std::vector<FormatStyle> Styles;
2007 llvm::yaml::Input Input(Config, /*Ctxt=*/nullptr, DiagHandler,
2008 DiagHandlerCtxt);
2009 // DocumentListTraits<vector<FormatStyle>> uses the context to get default
2010 // values for the fields, keys for which are missing from the configuration.
2011 // Mapping also uses the context to get the language to find the correct
2012 // base style.
2013 Input.setContext(Style);
2014 Input.setAllowUnknownKeys(AllowUnknownOptions);
2015 Input >> Styles;
2016 if (Input.error())
2017 return Input.error();
2018
2019 for (unsigned i = 0; i < Styles.size(); ++i) {
2020 // Ensures that only the first configuration can skip the Language option.
2021 if (Styles[i].Language == FormatStyle::LK_None && i != 0)
2023 // Ensure that each language is configured at most once.
2024 for (unsigned j = 0; j < i; ++j) {
2025 if (Styles[i].Language == Styles[j].Language) {
2026 LLVM_DEBUG(llvm::dbgs()
2027 << "Duplicate languages in the config file on positions "
2028 << j << " and " << i << "\n");
2030 }
2031 }
2032 }
2033 // Look for a suitable configuration starting from the end, so we can
2034 // find the configuration for the specific language first, and the default
2035 // configuration (which can only be at slot 0) after it.
2037 bool LanguageFound = false;
2038 for (const FormatStyle &Style : llvm::reverse(Styles)) {
2039 if (Style.Language != FormatStyle::LK_None)
2040 StyleSet.Add(Style);
2041 if (Style.Language == Language)
2042 LanguageFound = true;
2043 }
2044 if (!LanguageFound) {
2045 if (Styles.empty() || Styles[0].Language != FormatStyle::LK_None)
2047 FormatStyle DefaultStyle = Styles[0];
2048 DefaultStyle.Language = Language;
2049 StyleSet.Add(std::move(DefaultStyle));
2050 }
2051 *Style = *StyleSet.Get(Language);
2053 Style->BinPackArguments) {
2054 // See comment on FormatStyle::TSC_Wrapped.
2056 }
2060}
2061
2062std::string configurationAsText(const FormatStyle &Style) {
2063 std::string Text;
2064 llvm::raw_string_ostream Stream(Text);
2065 llvm::yaml::Output Output(Stream);
2066 // We use the same mapping method for input and output, so we need a non-const
2067 // reference here.
2068 FormatStyle NonConstStyle = Style;
2069 expandPresetsBraceWrapping(NonConstStyle);
2070 expandPresetsSpaceBeforeParens(NonConstStyle);
2071 expandPresetsSpacesInParens(NonConstStyle);
2072 Output << NonConstStyle;
2073
2074 return Stream.str();
2075}
2076
2077std::optional<FormatStyle>
2079 if (!Styles)
2080 return std::nullopt;
2081 auto It = Styles->find(Language);
2082 if (It == Styles->end())
2083 return std::nullopt;
2084 FormatStyle Style = It->second;
2085 Style.StyleSet = *this;
2086 return Style;
2087}
2088
2090 assert(Style.Language != LK_None &&
2091 "Cannot add a style for LK_None to a StyleSet");
2092 assert(
2093 !Style.StyleSet.Styles &&
2094 "Cannot add a style associated with an existing StyleSet to a StyleSet");
2095 if (!Styles)
2096 Styles = std::make_shared<MapType>();
2097 (*Styles)[Style.Language] = std::move(Style);
2098}
2099
2100void FormatStyle::FormatStyleSet::Clear() { Styles.reset(); }
2101
2102std::optional<FormatStyle>
2104 return StyleSet.Get(Language);
2105}
2106
2107namespace {
2108
2109class ParensRemover : public TokenAnalyzer {
2110public:
2111 ParensRemover(const Environment &Env, const FormatStyle &Style)
2112 : TokenAnalyzer(Env, Style) {}
2113
2114 std::pair<tooling::Replacements, unsigned>
2115 analyze(TokenAnnotator &Annotator,
2116 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2117 FormatTokenLexer &Tokens) override {
2118 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2119 tooling::Replacements Result;
2120 removeParens(AnnotatedLines, Result);
2121 return {Result, 0};
2122 }
2123
2124private:
2125 void removeParens(SmallVectorImpl<AnnotatedLine *> &Lines,
2126 tooling::Replacements &Result) {
2127 const auto &SourceMgr = Env.getSourceManager();
2128 for (auto *Line : Lines) {
2129 removeParens(Line->Children, Result);
2130 if (!Line->Affected)
2131 continue;
2132 for (const auto *Token = Line->First; Token && !Token->Finalized;
2133 Token = Token->Next) {
2134 if (!Token->Optional || !Token->isOneOf(tok::l_paren, tok::r_paren))
2135 continue;
2136 auto *Next = Token->Next;
2137 assert(Next && Next->isNot(tok::eof));
2138 SourceLocation Start;
2139 if (Next->NewlinesBefore == 0) {
2140 Start = Token->Tok.getLocation();
2141 Next->WhitespaceRange = Token->WhitespaceRange;
2142 } else {
2143 Start = Token->WhitespaceRange.getBegin();
2144 }
2145 const auto &Range =
2146 CharSourceRange::getCharRange(Start, Token->Tok.getEndLoc());
2147 cantFail(Result.add(tooling::Replacement(SourceMgr, Range, " ")));
2148 }
2149 }
2150 }
2151};
2152
2153class BracesInserter : public TokenAnalyzer {
2154public:
2155 BracesInserter(const Environment &Env, const FormatStyle &Style)
2156 : TokenAnalyzer(Env, Style) {}
2157
2158 std::pair<tooling::Replacements, unsigned>
2159 analyze(TokenAnnotator &Annotator,
2160 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2161 FormatTokenLexer &Tokens) override {
2162 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2163 tooling::Replacements Result;
2164 insertBraces(AnnotatedLines, Result);
2165 return {Result, 0};
2166 }
2167
2168private:
2169 void insertBraces(SmallVectorImpl<AnnotatedLine *> &Lines,
2170 tooling::Replacements &Result) {
2171 const auto &SourceMgr = Env.getSourceManager();
2172 int OpeningBraceSurplus = 0;
2173 for (AnnotatedLine *Line : Lines) {
2174 insertBraces(Line->Children, Result);
2175 if (!Line->Affected && OpeningBraceSurplus == 0)
2176 continue;
2177 for (FormatToken *Token = Line->First; Token && !Token->Finalized;
2178 Token = Token->Next) {
2179 int BraceCount = Token->BraceCount;
2180 if (BraceCount == 0)
2181 continue;
2182 std::string Brace;
2183 if (BraceCount < 0) {
2184 assert(BraceCount == -1);
2185 if (!Line->Affected)
2186 break;
2187 Brace = Token->is(tok::comment) ? "\n{" : "{";
2188 ++OpeningBraceSurplus;
2189 } else {
2190 if (OpeningBraceSurplus == 0)
2191 break;
2192 if (OpeningBraceSurplus < BraceCount)
2193 BraceCount = OpeningBraceSurplus;
2194 Brace = '\n' + std::string(BraceCount, '}');
2195 OpeningBraceSurplus -= BraceCount;
2196 }
2197 Token->BraceCount = 0;
2198 const auto Start = Token->Tok.getEndLoc();
2199 cantFail(Result.add(tooling::Replacement(SourceMgr, Start, 0, Brace)));
2200 }
2201 }
2202 assert(OpeningBraceSurplus == 0);
2203 }
2204};
2205
2206class BracesRemover : public TokenAnalyzer {
2207public:
2208 BracesRemover(const Environment &Env, const FormatStyle &Style)
2209 : TokenAnalyzer(Env, Style) {}
2210
2211 std::pair<tooling::Replacements, unsigned>
2212 analyze(TokenAnnotator &Annotator,
2213 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2214 FormatTokenLexer &Tokens) override {
2215 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2216 tooling::Replacements Result;
2217 removeBraces(AnnotatedLines, Result);
2218 return {Result, 0};
2219 }
2220
2221private:
2222 void removeBraces(SmallVectorImpl<AnnotatedLine *> &Lines,
2223 tooling::Replacements &Result) {
2224 const auto &SourceMgr = Env.getSourceManager();
2225 const auto End = Lines.end();
2226 for (auto I = Lines.begin(); I != End; ++I) {
2227 const auto Line = *I;
2228 removeBraces(Line->Children, Result);
2229 if (!Line->Affected)
2230 continue;
2231 const auto NextLine = I + 1 == End ? nullptr : I[1];
2232 for (auto Token = Line->First; Token && !Token->Finalized;
2233 Token = Token->Next) {
2234 if (!Token->Optional)
2235 continue;
2236 if (!Token->isOneOf(tok::l_brace, tok::r_brace))
2237 continue;
2238 auto Next = Token->Next;
2239 assert(Next || Token == Line->Last);
2240 if (!Next && NextLine)
2241 Next = NextLine->First;
2242 SourceLocation Start;
2243 if (Next && Next->NewlinesBefore == 0 && Next->isNot(tok::eof)) {
2244 Start = Token->Tok.getLocation();
2245 Next->WhitespaceRange = Token->WhitespaceRange;
2246 } else {
2247 Start = Token->WhitespaceRange.getBegin();
2248 }
2249 const auto Range =
2250 CharSourceRange::getCharRange(Start, Token->Tok.getEndLoc());
2251 cantFail(Result.add(tooling::Replacement(SourceMgr, Range, "")));
2252 }
2253 }
2254 }
2255};
2256
2257class SemiRemover : public TokenAnalyzer {
2258public:
2259 SemiRemover(const Environment &Env, const FormatStyle &Style)
2260 : TokenAnalyzer(Env, Style) {}
2261
2262 std::pair<tooling::Replacements, unsigned>
2263 analyze(TokenAnnotator &Annotator,
2264 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2265 FormatTokenLexer &Tokens) override {
2266 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2267 tooling::Replacements Result;
2268 removeSemi(Annotator, AnnotatedLines, Result);
2269 return {Result, 0};
2270 }
2271
2272private:
2273 void removeSemi(TokenAnnotator &Annotator,
2274 SmallVectorImpl<AnnotatedLine *> &Lines,
2275 tooling::Replacements &Result) {
2276 auto PrecededByFunctionRBrace = [](const FormatToken &Tok) {
2277 const auto *Prev = Tok.Previous;
2278 if (!Prev || Prev->isNot(tok::r_brace))
2279 return false;
2280 const auto *LBrace = Prev->MatchingParen;
2281 return LBrace && LBrace->is(TT_FunctionLBrace);
2282 };
2283 const auto &SourceMgr = Env.getSourceManager();
2284 const auto End = Lines.end();
2285 for (auto I = Lines.begin(); I != End; ++I) {
2286 const auto Line = *I;
2287 removeSemi(Annotator, Line->Children, Result);
2288 if (!Line->Affected)
2289 continue;
2290 Annotator.calculateFormattingInformation(*Line);
2291 const auto NextLine = I + 1 == End ? nullptr : I[1];
2292 for (auto Token = Line->First; Token && !Token->Finalized;
2293 Token = Token->Next) {
2294 if (Token->isNot(tok::semi) ||
2295 (!Token->Optional && !PrecededByFunctionRBrace(*Token))) {
2296 continue;
2297 }
2298 auto Next = Token->Next;
2299 assert(Next || Token == Line->Last);
2300 if (!Next && NextLine)
2301 Next = NextLine->First;
2302 SourceLocation Start;
2303 if (Next && Next->NewlinesBefore == 0 && Next->isNot(tok::eof)) {
2304 Start = Token->Tok.getLocation();
2305 Next->WhitespaceRange = Token->WhitespaceRange;
2306 } else {
2307 Start = Token->WhitespaceRange.getBegin();
2308 }
2309 const auto Range =
2310 CharSourceRange::getCharRange(Start, Token->Tok.getEndLoc());
2311 cantFail(Result.add(tooling::Replacement(SourceMgr, Range, "")));
2312 }
2313 }
2314 }
2315};
2316
2317class JavaScriptRequoter : public TokenAnalyzer {
2318public:
2319 JavaScriptRequoter(const Environment &Env, const FormatStyle &Style)
2320 : TokenAnalyzer(Env, Style) {}
2321
2322 std::pair<tooling::Replacements, unsigned>
2323 analyze(TokenAnnotator &Annotator,
2324 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2325 FormatTokenLexer &Tokens) override {
2326 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2327 tooling::Replacements Result;
2328 requoteJSStringLiteral(AnnotatedLines, Result);
2329 return {Result, 0};
2330 }
2331
2332private:
2333 // Replaces double/single-quoted string literal as appropriate, re-escaping
2334 // the contents in the process.
2335 void requoteJSStringLiteral(SmallVectorImpl<AnnotatedLine *> &Lines,
2336 tooling::Replacements &Result) {
2337 for (AnnotatedLine *Line : Lines) {
2338 requoteJSStringLiteral(Line->Children, Result);
2339 if (!Line->Affected)
2340 continue;
2341 for (FormatToken *FormatTok = Line->First; FormatTok;
2342 FormatTok = FormatTok->Next) {
2343 StringRef Input = FormatTok->TokenText;
2344 if (FormatTok->Finalized || !FormatTok->isStringLiteral() ||
2345 // NB: testing for not starting with a double quote to avoid
2346 // breaking `template strings`.
2347 (Style.JavaScriptQuotes == FormatStyle::JSQS_Single &&
2348 !Input.starts_with("\"")) ||
2349 (Style.JavaScriptQuotes == FormatStyle::JSQS_Double &&
2350 !Input.starts_with("\'"))) {
2351 continue;
2352 }
2353
2354 // Change start and end quote.
2355 bool IsSingle = Style.JavaScriptQuotes == FormatStyle::JSQS_Single;
2356 SourceLocation Start = FormatTok->Tok.getLocation();
2357 auto Replace = [&](SourceLocation Start, unsigned Length,
2358 StringRef ReplacementText) {
2359 auto Err = Result.add(tooling::Replacement(
2360 Env.getSourceManager(), Start, Length, ReplacementText));
2361 // FIXME: handle error. For now, print error message and skip the
2362 // replacement for release version.
2363 if (Err) {
2364 llvm::errs() << llvm::toString(std::move(Err)) << "\n";
2365 assert(false);
2366 }
2367 };
2368 Replace(Start, 1, IsSingle ? "'" : "\"");
2369 Replace(FormatTok->Tok.getEndLoc().getLocWithOffset(-1), 1,
2370 IsSingle ? "'" : "\"");
2371
2372 // Escape internal quotes.
2373 bool Escaped = false;
2374 for (size_t i = 1; i < Input.size() - 1; i++) {
2375 switch (Input[i]) {
2376 case '\\':
2377 if (!Escaped && i + 1 < Input.size() &&
2378 ((IsSingle && Input[i + 1] == '"') ||
2379 (!IsSingle && Input[i + 1] == '\''))) {
2380 // Remove this \, it's escaping a " or ' that no longer needs
2381 // escaping
2382 Replace(Start.getLocWithOffset(i), 1, "");
2383 continue;
2384 }
2385 Escaped = !Escaped;
2386 break;
2387 case '\"':
2388 case '\'':
2389 if (!Escaped && IsSingle == (Input[i] == '\'')) {
2390 // Escape the quote.
2391 Replace(Start.getLocWithOffset(i), 0, "\\");
2392 }
2393 Escaped = false;
2394 break;
2395 default:
2396 Escaped = false;
2397 break;
2398 }
2399 }
2400 }
2401 }
2402 }
2403};
2404
2405class Formatter : public TokenAnalyzer {
2406public:
2407 Formatter(const Environment &Env, const FormatStyle &Style,
2408 FormattingAttemptStatus *Status)
2409 : TokenAnalyzer(Env, Style), Status(Status) {}
2410
2411 std::pair<tooling::Replacements, unsigned>
2412 analyze(TokenAnnotator &Annotator,
2413 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2414 FormatTokenLexer &Tokens) override {
2415 tooling::Replacements Result;
2416 deriveLocalStyle(AnnotatedLines);
2417 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2418 for (AnnotatedLine *Line : AnnotatedLines)
2419 Annotator.calculateFormattingInformation(*Line);
2420 Annotator.setCommentLineLevels(AnnotatedLines);
2421
2422 WhitespaceManager Whitespaces(
2423 Env.getSourceManager(), Style,
2424 Style.LineEnding > FormatStyle::LE_CRLF
2425 ? WhitespaceManager::inputUsesCRLF(
2426 Env.getSourceManager().getBufferData(Env.getFileID()),
2427 Style.LineEnding == FormatStyle::LE_DeriveCRLF)
2428 : Style.LineEnding == FormatStyle::LE_CRLF);
2429 ContinuationIndenter Indenter(Style, Tokens.getKeywords(),
2430 Env.getSourceManager(), Whitespaces, Encoding,
2431 BinPackInconclusiveFunctions);
2432 unsigned Penalty =
2433 UnwrappedLineFormatter(&Indenter, &Whitespaces, Style,
2434 Tokens.getKeywords(), Env.getSourceManager(),
2435 Status)
2436 .format(AnnotatedLines, /*DryRun=*/false,
2437 /*AdditionalIndent=*/0,
2438 /*FixBadIndentation=*/false,
2439 /*FirstStartColumn=*/Env.getFirstStartColumn(),
2440 /*NextStartColumn=*/Env.getNextStartColumn(),
2441 /*LastStartColumn=*/Env.getLastStartColumn());
2442 for (const auto &R : Whitespaces.generateReplacements())
2443 if (Result.add(R))
2444 return std::make_pair(Result, 0);
2445 return std::make_pair(Result, Penalty);
2446 }
2447
2448private:
2449 bool
2450 hasCpp03IncompatibleFormat(const SmallVectorImpl<AnnotatedLine *> &Lines) {
2451 for (const AnnotatedLine *Line : Lines) {
2452 if (hasCpp03IncompatibleFormat(Line->Children))
2453 return true;
2454 for (FormatToken *Tok = Line->First->Next; Tok; Tok = Tok->Next) {
2455 if (!Tok->hasWhitespaceBefore()) {
2456 if (Tok->is(tok::coloncolon) && Tok->Previous->is(TT_TemplateOpener))
2457 return true;
2458 if (Tok->is(TT_TemplateCloser) &&
2459 Tok->Previous->is(TT_TemplateCloser)) {
2460 return true;
2461 }
2462 }
2463 }
2464 }
2465 return false;
2466 }
2467
2468 int countVariableAlignments(const SmallVectorImpl<AnnotatedLine *> &Lines) {
2469 int AlignmentDiff = 0;
2470 for (const AnnotatedLine *Line : Lines) {
2471 AlignmentDiff += countVariableAlignments(Line->Children);
2472 for (FormatToken *Tok = Line->First; Tok && Tok->Next; Tok = Tok->Next) {
2473 if (Tok->isNot(TT_PointerOrReference))
2474 continue;
2475 // Don't treat space in `void foo() &&` as evidence.
2476 if (const auto *Prev = Tok->getPreviousNonComment()) {
2477 if (Prev->is(tok::r_paren) && Prev->MatchingParen) {
2478 if (const auto *Func =
2479 Prev->MatchingParen->getPreviousNonComment()) {
2480 if (Func->isOneOf(TT_FunctionDeclarationName, TT_StartOfName,
2481 TT_OverloadedOperator)) {
2482 continue;
2483 }
2484 }
2485 }
2486 }
2487 bool SpaceBefore = Tok->hasWhitespaceBefore();
2488 bool SpaceAfter = Tok->Next->hasWhitespaceBefore();
2489 if (SpaceBefore && !SpaceAfter)
2490 ++AlignmentDiff;
2491 if (!SpaceBefore && SpaceAfter)
2492 --AlignmentDiff;
2493 }
2494 }
2495 return AlignmentDiff;
2496 }
2497
2498 void
2499 deriveLocalStyle(const SmallVectorImpl<AnnotatedLine *> &AnnotatedLines) {
2500 bool HasBinPackedFunction = false;
2501 bool HasOnePerLineFunction = false;
2502 for (AnnotatedLine *Line : AnnotatedLines) {
2503 if (!Line->First->Next)
2504 continue;
2505 FormatToken *Tok = Line->First->Next;
2506 while (Tok->Next) {
2507 if (Tok->is(PPK_BinPacked))
2508 HasBinPackedFunction = true;
2509 if (Tok->is(PPK_OnePerLine))
2510 HasOnePerLineFunction = true;
2511
2512 Tok = Tok->Next;
2513 }
2514 }
2515 if (Style.DerivePointerAlignment) {
2516 const auto NetRightCount = countVariableAlignments(AnnotatedLines);
2517 if (NetRightCount > 0)
2518 Style.PointerAlignment = FormatStyle::PAS_Right;
2519 else if (NetRightCount < 0)
2520 Style.PointerAlignment = FormatStyle::PAS_Left;
2521 Style.ReferenceAlignment = FormatStyle::RAS_Pointer;
2522 }
2523 if (Style.Standard == FormatStyle::LS_Auto) {
2524 Style.Standard = hasCpp03IncompatibleFormat(AnnotatedLines)
2525 ? FormatStyle::LS_Latest
2526 : FormatStyle::LS_Cpp03;
2527 }
2528 BinPackInconclusiveFunctions =
2529 HasBinPackedFunction || !HasOnePerLineFunction;
2530 }
2531
2532 bool BinPackInconclusiveFunctions;
2533 FormattingAttemptStatus *Status;
2534};
2535
2536/// TrailingCommaInserter inserts trailing commas into container literals.
2537/// E.g.:
2538/// const x = [
2539/// 1,
2540/// ];
2541/// TrailingCommaInserter runs after formatting. To avoid causing a required
2542/// reformatting (and thus reflow), it never inserts a comma that'd exceed the
2543/// ColumnLimit.
2544///
2545/// Because trailing commas disable binpacking of arrays, TrailingCommaInserter
2546/// is conceptually incompatible with bin packing.
2547class TrailingCommaInserter : public TokenAnalyzer {
2548public:
2549 TrailingCommaInserter(const Environment &Env, const FormatStyle &Style)
2550 : TokenAnalyzer(Env, Style) {}
2551
2552 std::pair<tooling::Replacements, unsigned>
2553 analyze(TokenAnnotator &Annotator,
2554 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2555 FormatTokenLexer &Tokens) override {
2556 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2557 tooling::Replacements Result;
2558 insertTrailingCommas(AnnotatedLines, Result);
2559 return {Result, 0};
2560 }
2561
2562private:
2563 /// Inserts trailing commas in [] and {} initializers if they wrap over
2564 /// multiple lines.
2565 void insertTrailingCommas(SmallVectorImpl<AnnotatedLine *> &Lines,
2566 tooling::Replacements &Result) {
2567 for (AnnotatedLine *Line : Lines) {
2568 insertTrailingCommas(Line->Children, Result);
2569 if (!Line->Affected)
2570 continue;
2571 for (FormatToken *FormatTok = Line->First; FormatTok;
2572 FormatTok = FormatTok->Next) {
2573 if (FormatTok->NewlinesBefore == 0)
2574 continue;
2575 FormatToken *Matching = FormatTok->MatchingParen;
2576 if (!Matching || !FormatTok->getPreviousNonComment())
2577 continue;
2578 if (!(FormatTok->is(tok::r_square) &&
2579 Matching->is(TT_ArrayInitializerLSquare)) &&
2580 !(FormatTok->is(tok::r_brace) && Matching->is(TT_DictLiteral))) {
2581 continue;
2582 }
2583 FormatToken *Prev = FormatTok->getPreviousNonComment();
2584 if (Prev->is(tok::comma) || Prev->is(tok::semi))
2585 continue;
2586 // getEndLoc is not reliably set during re-lexing, use text length
2587 // instead.
2588 SourceLocation Start =
2589 Prev->Tok.getLocation().getLocWithOffset(Prev->TokenText.size());
2590 // If inserting a comma would push the code over the column limit, skip
2591 // this location - it'd introduce an unstable formatting due to the
2592 // required reflow.
2593 unsigned ColumnNumber =
2594 Env.getSourceManager().getSpellingColumnNumber(Start);
2595 if (ColumnNumber > Style.ColumnLimit)
2596 continue;
2597 // Comma insertions cannot conflict with each other, and this pass has a
2598 // clean set of Replacements, so the operation below cannot fail.
2599 cantFail(Result.add(
2600 tooling::Replacement(Env.getSourceManager(), Start, 0, ",")));
2601 }
2602 }
2603 }
2604};
2605
2606// This class clean up the erroneous/redundant code around the given ranges in
2607// file.
2608class Cleaner : public TokenAnalyzer {
2609public:
2610 Cleaner(const Environment &Env, const FormatStyle &Style)
2611 : TokenAnalyzer(Env, Style),
2612 DeletedTokens(FormatTokenLess(Env.getSourceManager())) {}
2613
2614 // FIXME: eliminate unused parameters.
2615 std::pair<tooling::Replacements, unsigned>
2616 analyze(TokenAnnotator &Annotator,
2617 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2618 FormatTokenLexer &Tokens) override {
2619 // FIXME: in the current implementation the granularity of affected range
2620 // is an annotated line. However, this is not sufficient. Furthermore,
2621 // redundant code introduced by replacements does not necessarily
2622 // intercept with ranges of replacements that result in the redundancy.
2623 // To determine if some redundant code is actually introduced by
2624 // replacements(e.g. deletions), we need to come up with a more
2625 // sophisticated way of computing affected ranges.
2626 AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
2627
2628 checkEmptyNamespace(AnnotatedLines);
2629
2630 for (auto *Line : AnnotatedLines)
2631 cleanupLine(Line);
2632
2633 return {generateFixes(), 0};
2634 }
2635
2636private:
2637 void cleanupLine(AnnotatedLine *Line) {
2638 for (auto *Child : Line->Children)
2639 cleanupLine(Child);
2640
2641 if (Line->Affected) {
2642 cleanupRight(Line->First, tok::comma, tok::comma);
2643 cleanupRight(Line->First, TT_CtorInitializerColon, tok::comma);
2644 cleanupRight(Line->First, tok::l_paren, tok::comma);
2645 cleanupLeft(Line->First, tok::comma, tok::r_paren);
2646 cleanupLeft(Line->First, TT_CtorInitializerComma, tok::l_brace);
2647 cleanupLeft(Line->First, TT_CtorInitializerColon, tok::l_brace);
2648 cleanupLeft(Line->First, TT_CtorInitializerColon, tok::equal);
2649 }
2650 }
2651
2652 bool containsOnlyComments(const AnnotatedLine &Line) {
2653 for (FormatToken *Tok = Line.First; Tok; Tok = Tok->Next)
2654 if (Tok->isNot(tok::comment))
2655 return false;
2656 return true;
2657 }
2658
2659 // Iterate through all lines and remove any empty (nested) namespaces.
2660 void checkEmptyNamespace(SmallVectorImpl<AnnotatedLine *> &AnnotatedLines) {
2661 std::set<unsigned> DeletedLines;
2662 for (unsigned i = 0, e = AnnotatedLines.size(); i != e; ++i) {
2663 auto &Line = *AnnotatedLines[i];
2664 if (Line.startsWithNamespace())
2665 checkEmptyNamespace(AnnotatedLines, i, i, DeletedLines);
2666 }
2667
2668 for (auto Line : DeletedLines) {
2669 FormatToken *Tok = AnnotatedLines[Line]->First;
2670 while (Tok) {
2671 deleteToken(Tok);
2672 Tok = Tok->Next;
2673 }
2674 }
2675 }
2676
2677 // The function checks if the namespace, which starts from \p CurrentLine, and
2678 // its nested namespaces are empty and delete them if they are empty. It also
2679 // sets \p NewLine to the last line checked.
2680 // Returns true if the current namespace is empty.
2681 bool checkEmptyNamespace(SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2682 unsigned CurrentLine, unsigned &NewLine,
2683 std::set<unsigned> &DeletedLines) {
2684 unsigned InitLine = CurrentLine, End = AnnotatedLines.size();
2685 if (Style.BraceWrapping.AfterNamespace) {
2686 // If the left brace is in a new line, we should consume it first so that
2687 // it does not make the namespace non-empty.
2688 // FIXME: error handling if there is no left brace.
2689 if (!AnnotatedLines[++CurrentLine]->startsWith(tok::l_brace)) {
2690 NewLine = CurrentLine;
2691 return false;
2692 }
2693 } else if (!AnnotatedLines[CurrentLine]->endsWith(tok::l_brace)) {
2694 return false;
2695 }
2696 while (++CurrentLine < End) {
2697 if (AnnotatedLines[CurrentLine]->startsWith(tok::r_brace))
2698 break;
2699
2700 if (AnnotatedLines[CurrentLine]->startsWithNamespace()) {
2701 if (!checkEmptyNamespace(AnnotatedLines, CurrentLine, NewLine,
2702 DeletedLines)) {
2703 return false;
2704 }
2705 CurrentLine = NewLine;
2706 continue;
2707 }
2708
2709 if (containsOnlyComments(*AnnotatedLines[CurrentLine]))
2710 continue;
2711
2712 // If there is anything other than comments or nested namespaces in the
2713 // current namespace, the namespace cannot be empty.
2714 NewLine = CurrentLine;
2715 return false;
2716 }
2717
2718 NewLine = CurrentLine;
2719 if (CurrentLine >= End)
2720 return false;
2721
2722 // Check if the empty namespace is actually affected by changed ranges.
2723 if (!AffectedRangeMgr.affectsCharSourceRange(CharSourceRange::getCharRange(
2724 AnnotatedLines[InitLine]->First->Tok.getLocation(),
2725 AnnotatedLines[CurrentLine]->Last->Tok.getEndLoc()))) {
2726 return false;
2727 }
2728
2729 for (unsigned i = InitLine; i <= CurrentLine; ++i)
2730 DeletedLines.insert(i);
2731
2732 return true;
2733 }
2734
2735 // Checks pairs {start, start->next},..., {end->previous, end} and deletes one
2736 // of the token in the pair if the left token has \p LK token kind and the
2737 // right token has \p RK token kind. If \p DeleteLeft is true, the left token
2738 // is deleted on match; otherwise, the right token is deleted.
2739 template <typename LeftKind, typename RightKind>
2740 void cleanupPair(FormatToken *Start, LeftKind LK, RightKind RK,
2741 bool DeleteLeft) {
2742 auto NextNotDeleted = [this](const FormatToken &Tok) -> FormatToken * {
2743 for (auto *Res = Tok.Next; Res; Res = Res->Next) {
2744 if (Res->isNot(tok::comment) &&
2745 DeletedTokens.find(Res) == DeletedTokens.end()) {
2746 return Res;
2747 }
2748 }
2749 return nullptr;
2750 };
2751 for (auto *Left = Start; Left;) {
2752 auto *Right = NextNotDeleted(*Left);
2753 if (!Right)
2754 break;
2755 if (Left->is(LK) && Right->is(RK)) {
2756 deleteToken(DeleteLeft ? Left : Right);
2757 for (auto *Tok = Left->Next; Tok && Tok != Right; Tok = Tok->Next)
2758 deleteToken(Tok);
2759 // If the right token is deleted, we should keep the left token
2760 // unchanged and pair it with the new right token.
2761 if (!DeleteLeft)
2762 continue;
2763 }
2764 Left = Right;
2765 }
2766 }
2767
2768 template <typename LeftKind, typename RightKind>
2769 void cleanupLeft(FormatToken *Start, LeftKind LK, RightKind RK) {
2770 cleanupPair(Start, LK, RK, /*DeleteLeft=*/true);
2771 }
2772
2773 template <typename LeftKind, typename RightKind>
2774 void cleanupRight(FormatToken *Start, LeftKind LK, RightKind RK) {
2775 cleanupPair(Start, LK, RK, /*DeleteLeft=*/false);
2776 }
2777
2778 // Delete the given token.
2779 inline void deleteToken(FormatToken *Tok) {
2780 if (Tok)
2781 DeletedTokens.insert(Tok);
2782 }
2783
2784 tooling::Replacements generateFixes() {
2785 tooling::Replacements Fixes;
2786 SmallVector<FormatToken *> Tokens;
2787 std::copy(DeletedTokens.begin(), DeletedTokens.end(),
2788 std::back_inserter(Tokens));
2789
2790 // Merge multiple continuous token deletions into one big deletion so that
2791 // the number of replacements can be reduced. This makes computing affected
2792 // ranges more efficient when we run reformat on the changed code.
2793 unsigned Idx = 0;
2794 while (Idx < Tokens.size()) {
2795 unsigned St = Idx, End = Idx;
2796 while ((End + 1) < Tokens.size() && Tokens[End]->Next == Tokens[End + 1])
2797 ++End;
2798 auto SR = CharSourceRange::getCharRange(Tokens[St]->Tok.getLocation(),
2799 Tokens[End]->Tok.getEndLoc());
2800 auto Err =
2801 Fixes.add(tooling::Replacement(Env.getSourceManager(), SR, ""));
2802 // FIXME: better error handling. for now just print error message and skip
2803 // for the release version.
2804 if (Err) {
2805 llvm::errs() << llvm::toString(std::move(Err)) << "\n";
2806 assert(false && "Fixes must not conflict!");
2807 }
2808 Idx = End + 1;
2809 }
2810
2811 return Fixes;
2812 }
2813
2814 // Class for less-than inequality comparason for the set `RedundantTokens`.
2815 // We store tokens in the order they appear in the translation unit so that
2816 // we do not need to sort them in `generateFixes()`.
2817 struct FormatTokenLess {
2818 FormatTokenLess(const SourceManager &SM) : SM(SM) {}
2819
2820 bool operator()(const FormatToken *LHS, const FormatToken *RHS) const {
2821 return SM.isBeforeInTranslationUnit(LHS->Tok.getLocation(),
2822 RHS->Tok.getLocation());
2823 }
2824 const SourceManager &SM;
2825 };
2826
2827 // Tokens to be deleted.
2828 std::set<FormatToken *, FormatTokenLess> DeletedTokens;
2829};
2830
2831class ObjCHeaderStyleGuesser : public TokenAnalyzer {
2832public:
2833 ObjCHeaderStyleGuesser(const Environment &Env, const FormatStyle &Style)
2834 : TokenAnalyzer(Env, Style), IsObjC(false) {}
2835
2836 std::pair<tooling::Replacements, unsigned>
2837 analyze(TokenAnnotator &Annotator,
2838 SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2839 FormatTokenLexer &Tokens) override {
2840 assert(Style.Language == FormatStyle::LK_Cpp);
2841 IsObjC = guessIsObjC(Env.getSourceManager(), AnnotatedLines,
2842 Tokens.getKeywords());
2843 tooling::Replacements Result;
2844 return {Result, 0};
2845 }
2846
2847 bool isObjC() { return IsObjC; }
2848
2849private:
2850 static bool
2851 guessIsObjC(const SourceManager &SourceManager,
2852 const SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
2853 const AdditionalKeywords &Keywords) {
2854 // Keep this array sorted, since we are binary searching over it.
2855 static constexpr llvm::StringLiteral FoundationIdentifiers[] = {
2856 "CGFloat",
2857 "CGPoint",
2858 "CGPointMake",
2859 "CGPointZero",
2860 "CGRect",
2861 "CGRectEdge",
2862 "CGRectInfinite",
2863 "CGRectMake",
2864 "CGRectNull",
2865 "CGRectZero",
2866 "CGSize",
2867 "CGSizeMake",
2868 "CGVector",
2869 "CGVectorMake",
2870 "FOUNDATION_EXPORT", // This is an alias for FOUNDATION_EXTERN.
2871 "FOUNDATION_EXTERN",
2872 "NSAffineTransform",
2873 "NSArray",
2874 "NSAttributedString",
2875 "NSBlockOperation",
2876 "NSBundle",
2877 "NSCache",
2878 "NSCalendar",
2879 "NSCharacterSet",
2880 "NSCountedSet",
2881 "NSData",
2882 "NSDataDetector",
2883 "NSDecimal",
2884 "NSDecimalNumber",
2885 "NSDictionary",
2886 "NSEdgeInsets",
2887 "NSError",
2888 "NSErrorDomain",
2889 "NSHashTable",
2890 "NSIndexPath",
2891 "NSIndexSet",
2892 "NSInteger",
2893 "NSInvocationOperation",
2894 "NSLocale",
2895 "NSMapTable",
2896 "NSMutableArray",
2897 "NSMutableAttributedString",
2898 "NSMutableCharacterSet",
2899 "NSMutableData",
2900 "NSMutableDictionary",
2901 "NSMutableIndexSet",
2902 "NSMutableOrderedSet",
2903 "NSMutableSet",
2904 "NSMutableString",
2905 "NSNumber",
2906 "NSNumberFormatter",
2907 "NSObject",
2908 "NSOperation",
2909 "NSOperationQueue",
2910 "NSOperationQueuePriority",
2911 "NSOrderedSet",
2912 "NSPoint",
2913 "NSPointerArray",
2914 "NSQualityOfService",
2915 "NSRange",
2916 "NSRect",
2917 "NSRegularExpression",
2918 "NSSet",
2919 "NSSize",
2920 "NSString",
2921 "NSTimeZone",
2922 "NSUInteger",
2923 "NSURL",
2924 "NSURLComponents",
2925 "NSURLQueryItem",
2926 "NSUUID",
2927 "NSValue",
2928 "NS_ASSUME_NONNULL_BEGIN",
2929 "UIImage",
2930 "UIView",
2931 };
2932
2933 for (auto *Line : AnnotatedLines) {
2934 if (Line->First && (Line->First->TokenText.starts_with("#") ||
2935 Line->First->TokenText == "__pragma" ||
2936 Line->First->TokenText == "_Pragma")) {
2937 continue;
2938 }
2939 for (const FormatToken *FormatTok = Line->First; FormatTok;
2940 FormatTok = FormatTok->Next) {
2941 if ((FormatTok->Previous && FormatTok->Previous->is(tok::at) &&
2942 (FormatTok->Tok.getObjCKeywordID() != tok::objc_not_keyword ||
2943 FormatTok->isOneOf(tok::numeric_constant, tok::l_square,
2944 tok::l_brace))) ||
2945 (FormatTok->Tok.isAnyIdentifier() &&
2946 std::binary_search(std::begin(FoundationIdentifiers),
2947 std::end(FoundationIdentifiers),
2948 FormatTok->TokenText)) ||
2949 FormatTok->is(TT_ObjCStringLiteral) ||
2950 FormatTok->isOneOf(Keywords.kw_NS_CLOSED_ENUM, Keywords.kw_NS_ENUM,
2951 Keywords.kw_NS_ERROR_ENUM,
2952 Keywords.kw_NS_OPTIONS, TT_ObjCBlockLBrace,
2953 TT_ObjCBlockLParen, TT_ObjCDecl, TT_ObjCForIn,
2954 TT_ObjCMethodExpr, TT_ObjCMethodSpecifier,
2955 TT_ObjCProperty)) {
2956 LLVM_DEBUG(llvm::dbgs()
2957 << "Detected ObjC at location "
2958 << FormatTok->Tok.getLocation().printToString(
2959 SourceManager)
2960 << " token: " << FormatTok->TokenText << " token type: "
2961 << getTokenTypeName(FormatTok->getType()) << "\n");
2962 return true;
2963 }
2964 }
2965 if (guessIsObjC(SourceManager, Line->Children, Keywords))
2966 return true;
2967 }
2968 return false;
2969 }
2970
2971 bool IsObjC;
2972};
2973
2974struct IncludeDirective {
2975 StringRef Filename;
2976 StringRef Text;
2977 unsigned Offset;
2980};
2981
2982struct JavaImportDirective {
2983 StringRef Identifier;
2984 StringRef Text;
2985 unsigned Offset;
2986 SmallVector<StringRef> AssociatedCommentLines;
2988};
2989
2990} // end anonymous namespace
2991
2992// Determines whether 'Ranges' intersects with ('Start', 'End').
2993static bool affectsRange(ArrayRef<tooling::Range> Ranges, unsigned Start,
2994 unsigned End) {
2995 for (const auto &Range : Ranges) {
2996 if (Range.getOffset() < End &&
2997 Range.getOffset() + Range.getLength() > Start) {
2998 return true;
2999 }
3000 }
3001 return false;
3002}
3003
3004// Returns a pair (Index, OffsetToEOL) describing the position of the cursor
3005// before sorting/deduplicating. Index is the index of the include under the
3006// cursor in the original set of includes. If this include has duplicates, it is
3007// the index of the first of the duplicates as the others are going to be
3008// removed. OffsetToEOL describes the cursor's position relative to the end of
3009// its current line.
3010// If `Cursor` is not on any #include, `Index` will be UINT_MAX.
3011static std::pair<unsigned, unsigned>
3013 const SmallVectorImpl<unsigned> &Indices, unsigned Cursor) {
3014 unsigned CursorIndex = UINT_MAX;
3015 unsigned OffsetToEOL = 0;
3016 for (int i = 0, e = Includes.size(); i != e; ++i) {
3017 unsigned Start = Includes[Indices[i]].Offset;
3018 unsigned End = Start + Includes[Indices[i]].Text.size();
3019 if (!(Cursor >= Start && Cursor < End))
3020 continue;
3021 CursorIndex = Indices[i];
3022 OffsetToEOL = End - Cursor;
3023 // Put the cursor on the only remaining #include among the duplicate
3024 // #includes.
3025 while (--i >= 0 && Includes[CursorIndex].Text == Includes[Indices[i]].Text)
3026 CursorIndex = i;
3027 break;
3028 }
3029 return std::make_pair(CursorIndex, OffsetToEOL);
3030}
3031
3032// Replace all "\r\n" with "\n".
3033std::string replaceCRLF(const std::string &Code) {
3034 std::string NewCode;
3035 size_t Pos = 0, LastPos = 0;
3036
3037 do {
3038 Pos = Code.find("\r\n", LastPos);
3039 if (Pos == LastPos) {
3040 ++LastPos;
3041 continue;
3042 }
3043 if (Pos == std::string::npos) {
3044 NewCode += Code.substr(LastPos);
3045 break;
3046 }
3047 NewCode += Code.substr(LastPos, Pos - LastPos) + "\n";
3048 LastPos = Pos + 2;
3049 } while (Pos != std::string::npos);
3050
3051 return NewCode;
3052}
3053
3054// Sorts and deduplicate a block of includes given by 'Includes' alphabetically
3055// adding the necessary replacement to 'Replaces'. 'Includes' must be in strict
3056// source order.
3057// #include directives with the same text will be deduplicated, and only the
3058// first #include in the duplicate #includes remains. If the `Cursor` is
3059// provided and put on a deleted #include, it will be moved to the remaining
3060// #include in the duplicate #includes.
3061static void sortCppIncludes(const FormatStyle &Style,
3062 const SmallVectorImpl<IncludeDirective> &Includes,
3063 ArrayRef<tooling::Range> Ranges, StringRef FileName,
3064 StringRef Code, tooling::Replacements &Replaces,
3065 unsigned *Cursor) {
3067 const unsigned IncludesBeginOffset = Includes.front().Offset;
3068 const unsigned IncludesEndOffset =
3069 Includes.back().Offset + Includes.back().Text.size();
3070 const unsigned IncludesBlockSize = IncludesEndOffset - IncludesBeginOffset;
3071 if (!affectsRange(Ranges, IncludesBeginOffset, IncludesEndOffset))
3072 return;
3074 llvm::to_vector<16>(llvm::seq<unsigned>(0, Includes.size()));
3075
3077 llvm::stable_sort(Indices, [&](unsigned LHSI, unsigned RHSI) {
3078 const auto LHSFilenameLower = Includes[LHSI].Filename.lower();
3079 const auto RHSFilenameLower = Includes[RHSI].Filename.lower();
3080 return std::tie(Includes[LHSI].Priority, LHSFilenameLower,
3081 Includes[LHSI].Filename) <
3082 std::tie(Includes[RHSI].Priority, RHSFilenameLower,
3083 Includes[RHSI].Filename);
3084 });
3085 } else {
3086 llvm::stable_sort(Indices, [&](unsigned LHSI, unsigned RHSI) {
3087 return std::tie(Includes[LHSI].Priority, Includes[LHSI].Filename) <
3088 std::tie(Includes[RHSI].Priority, Includes[RHSI].Filename);
3089 });
3090 }
3091
3092 // The index of the include on which the cursor will be put after
3093 // sorting/deduplicating.
3094 unsigned CursorIndex;
3095 // The offset from cursor to the end of line.
3096 unsigned CursorToEOLOffset;
3097 if (Cursor) {
3098 std::tie(CursorIndex, CursorToEOLOffset) =
3099 FindCursorIndex(Includes, Indices, *Cursor);
3100 }
3101
3102 // Deduplicate #includes.
3103 Indices.erase(std::unique(Indices.begin(), Indices.end(),
3104 [&](unsigned LHSI, unsigned RHSI) {
3105 return Includes[LHSI].Text.trim() ==
3106 Includes[RHSI].Text.trim();
3107 }),
3108 Indices.end());
3109
3110 int CurrentCategory = Includes.front().Category;
3111
3112 // If the #includes are out of order, we generate a single replacement fixing
3113 // the entire block. Otherwise, no replacement is generated.
3114 // In case Style.IncldueStyle.IncludeBlocks != IBS_Preserve, this check is not
3115 // enough as additional newlines might be added or removed across #include
3116 // blocks. This we handle below by generating the updated #include blocks and
3117 // comparing it to the original.
3118 if (Indices.size() == Includes.size() && llvm::is_sorted(Indices) &&
3120 return;
3121 }
3122
3123 const auto OldCursor = Cursor ? *Cursor : 0;
3124 std::string result;
3125 for (unsigned Index : Indices) {
3126 if (!result.empty()) {
3127 result += "\n";
3128 if (Style.IncludeStyle.IncludeBlocks ==
3130 CurrentCategory != Includes[Index].Category) {
3131 result += "\n";
3132 }
3133 }
3134 result += Includes[Index].Text;
3135 if (Cursor && CursorIndex == Index)
3136 *Cursor = IncludesBeginOffset + result.size() - CursorToEOLOffset;
3137 CurrentCategory = Includes[Index].Category;
3138 }
3139
3140 if (Cursor && *Cursor >= IncludesEndOffset)
3141 *Cursor += result.size() - IncludesBlockSize;
3142
3143 // If the #includes are out of order, we generate a single replacement fixing
3144 // the entire range of blocks. Otherwise, no replacement is generated.
3145 if (replaceCRLF(result) == replaceCRLF(std::string(Code.substr(
3146 IncludesBeginOffset, IncludesBlockSize)))) {
3147 if (Cursor)
3148 *Cursor = OldCursor;
3149 return;
3150 }
3151
3152 auto Err = Replaces.add(tooling::Replacement(
3153 FileName, Includes.front().Offset, IncludesBlockSize, result));
3154 // FIXME: better error handling. For now, just skip the replacement for the
3155 // release version.
3156 if (Err) {
3157 llvm::errs() << llvm::toString(std::move(Err)) << "\n";
3158 assert(false);
3159 }
3160}
3161
3164 StringRef FileName,
3165 tooling::Replacements &Replaces,
3166 unsigned *Cursor) {
3167 unsigned Prev = llvm::StringSwitch<size_t>(Code)
3168 .StartsWith("\xEF\xBB\xBF", 3) // UTF-8 BOM
3169 .Default(0);
3170 unsigned SearchFrom = 0;
3172 SmallVector<IncludeDirective, 16> IncludesInBlock;
3173
3174 // In compiled files, consider the first #include to be the main #include of
3175 // the file if it is not a system #include. This ensures that the header
3176 // doesn't have hidden dependencies
3177 // (http://llvm.org/docs/CodingStandards.html#include-style).
3178 //
3179 // FIXME: Do some validation, e.g. edit distance of the base name, to fix
3180 // cases where the first #include is unlikely to be the main header.
3182 bool FirstIncludeBlock = true;
3183 bool MainIncludeFound = false;
3184 bool FormattingOff = false;
3185
3186 // '[' must be the first and '-' the last character inside [...].
3187 llvm::Regex RawStringRegex(
3188 "R\"([][A-Za-z0-9_{}#<>%:;.?*+/^&\\$|~!=,'-]*)\\(");
3189 SmallVector<StringRef, 2> RawStringMatches;
3190 std::string RawStringTermination = ")\"";
3191
3192 for (;;) {
3193 auto Pos = Code.find('\n', SearchFrom);
3194 StringRef Line =
3195 Code.substr(Prev, (Pos != StringRef::npos ? Pos : Code.size()) - Prev);
3196
3197 StringRef Trimmed = Line.trim();
3198
3199 // #includes inside raw string literals need to be ignored.
3200 // or we will sort the contents of the string.
3201 // Skip past until we think we are at the rawstring literal close.
3202 if (RawStringRegex.match(Trimmed, &RawStringMatches)) {
3203 std::string CharSequence = RawStringMatches[1].str();
3204 RawStringTermination = ")" + CharSequence + "\"";
3205 FormattingOff = true;
3206 }
3207
3208 if (Trimmed.contains(RawStringTermination))
3209 FormattingOff = false;
3210
3211 if (isClangFormatOff(Trimmed))
3212 FormattingOff = true;
3213 else if (isClangFormatOn(Trimmed))
3214 FormattingOff = false;
3215
3216 const bool EmptyLineSkipped =
3217 Trimmed.empty() &&
3221
3222 bool MergeWithNextLine = Trimmed.ends_with("\\");
3223 if (!FormattingOff && !MergeWithNextLine) {
3225 StringRef IncludeName = Matches[2];
3226 if (Line.contains("/*") && !Line.contains("*/")) {
3227 // #include with a start of a block comment, but without the end.
3228 // Need to keep all the lines until the end of the comment together.
3229 // FIXME: This is somehow simplified check that probably does not work
3230 // correctly if there are multiple comments on a line.
3231 Pos = Code.find("*/", SearchFrom);
3232 Line = Code.substr(
3233 Prev, (Pos != StringRef::npos ? Pos + 2 : Code.size()) - Prev);
3234 }
3235 int Category = Categories.getIncludePriority(
3236 IncludeName,
3237 /*CheckMainHeader=*/!MainIncludeFound && FirstIncludeBlock);
3238 int Priority = Categories.getSortIncludePriority(
3239 IncludeName, !MainIncludeFound && FirstIncludeBlock);
3240 if (Category == 0)
3241 MainIncludeFound = true;
3242 IncludesInBlock.push_back(
3243 {IncludeName, Line, Prev, Category, Priority});
3244 } else if (!IncludesInBlock.empty() && !EmptyLineSkipped) {
3245 sortCppIncludes(Style, IncludesInBlock, Ranges, FileName, Code,
3246 Replaces, Cursor);
3247 IncludesInBlock.clear();
3248 if (Trimmed.starts_with("#pragma hdrstop")) // Precompiled headers.
3249 FirstIncludeBlock = true;
3250 else
3251 FirstIncludeBlock = false;
3252 }
3253 }
3254 if (Pos == StringRef::npos || Pos + 1 == Code.size())
3255 break;
3256
3257 if (!MergeWithNextLine)
3258 Prev = Pos + 1;
3259 SearchFrom = Pos + 1;
3260 }
3261 if (!IncludesInBlock.empty()) {
3262 sortCppIncludes(Style, IncludesInBlock, Ranges, FileName, Code, Replaces,
3263 Cursor);
3264 }
3265 return Replaces;
3266}
3267
3268// Returns group number to use as a first order sort on imports. Gives UINT_MAX
3269// if the import does not match any given groups.
3270static unsigned findJavaImportGroup(const FormatStyle &Style,
3271 StringRef ImportIdentifier) {
3272 unsigned LongestMatchIndex = UINT_MAX;
3273 unsigned LongestMatchLength = 0;
3274 for (unsigned I = 0; I < Style.JavaImportGroups.size(); I++) {
3275 const std::string &GroupPrefix = Style.JavaImportGroups[I];
3276 if (ImportIdentifier.starts_with(GroupPrefix) &&
3277 GroupPrefix.length() > LongestMatchLength) {
3278 LongestMatchIndex = I;
3279 LongestMatchLength = GroupPrefix.length();
3280 }
3281 }
3282 return LongestMatchIndex;
3283}
3284
3285// Sorts and deduplicates a block of includes given by 'Imports' based on
3286// JavaImportGroups, then adding the necessary replacement to 'Replaces'.
3287// Import declarations with the same text will be deduplicated. Between each
3288// import group, a newline is inserted, and within each import group, a
3289// lexicographic sort based on ASCII value is performed.
3290static void sortJavaImports(const FormatStyle &Style,
3292 ArrayRef<tooling::Range> Ranges, StringRef FileName,
3293 StringRef Code, tooling::Replacements &Replaces) {
3294 unsigned ImportsBeginOffset = Imports.front().Offset;
3295 unsigned ImportsEndOffset =
3296 Imports.back().Offset + Imports.back().Text.size();
3297 unsigned ImportsBlockSize = ImportsEndOffset - ImportsBeginOffset;
3298 if (!affectsRange(Ranges, ImportsBeginOffset, ImportsEndOffset))
3299 return;
3300
3302 llvm::to_vector<16>(llvm::seq<unsigned>(0, Imports.size()));
3304 JavaImportGroups.reserve(Imports.size());
3305 for (const JavaImportDirective &Import : Imports)
3306 JavaImportGroups.push_back(findJavaImportGroup(Style, Import.Identifier));
3307
3308 bool StaticImportAfterNormalImport =
3310 llvm::sort(Indices, [&](unsigned LHSI, unsigned RHSI) {
3311 // Negating IsStatic to push static imports above non-static imports.
3312 return std::make_tuple(!Imports[LHSI].IsStatic ^
3313 StaticImportAfterNormalImport,
3314 JavaImportGroups[LHSI], Imports[LHSI].Identifier) <
3315 std::make_tuple(!Imports[RHSI].IsStatic ^
3316 StaticImportAfterNormalImport,
3317 JavaImportGroups[RHSI], Imports[RHSI].Identifier);
3318 });
3319
3320 // Deduplicate imports.
3321 Indices.erase(std::unique(Indices.begin(), Indices.end(),
3322 [&](unsigned LHSI, unsigned RHSI) {
3323 return Imports[LHSI].Text == Imports[RHSI].Text;
3324 }),
3325 Indices.end());
3326
3327 bool CurrentIsStatic = Imports[Indices.front()].IsStatic;
3328 unsigned CurrentImportGroup = JavaImportGroups[Indices.front()];
3329
3330 std::string result;
3331 for (unsigned Index : Indices) {
3332 if (!result.empty()) {
3333 result += "\n";
3334 if (CurrentIsStatic != Imports[Index].IsStatic ||
3335 CurrentImportGroup != JavaImportGroups[Index]) {
3336 result += "\n";
3337 }
3338 }
3339 for (StringRef CommentLine : Imports[Index].AssociatedCommentLines) {
3340 result += CommentLine;
3341 result += "\n";
3342 }
3343 result += Imports[Index].Text;
3344 CurrentIsStatic = Imports[Index].IsStatic;
3345 CurrentImportGroup = JavaImportGroups[Index];
3346 }
3347
3348 // If the imports are out of order, we generate a single replacement fixing
3349 // the entire block. Otherwise, no replacement is generated.
3350 if (replaceCRLF(result) == replaceCRLF(std::string(Code.substr(
3351 Imports.front().Offset, ImportsBlockSize)))) {
3352 return;
3353 }
3354
3355 auto Err = Replaces.add(tooling::Replacement(FileName, Imports.front().Offset,
3356 ImportsBlockSize, result));
3357 // FIXME: better error handling. For now, just skip the replacement for the
3358 // release version.
3359 if (Err) {
3360 llvm::errs() << llvm::toString(std::move(Err)) << "\n";
3361 assert(false);
3362 }
3363}
3364
3365namespace {
3366
3367const char JavaImportRegexPattern[] =
3368 "^[\t ]*import[\t ]+(static[\t ]*)?([^\t ]*)[\t ]*;";
3369
3370} // anonymous namespace
3371
3374 StringRef FileName,
3375 tooling::Replacements &Replaces) {
3376 unsigned Prev = 0;
3377 unsigned SearchFrom = 0;
3378 llvm::Regex ImportRegex(JavaImportRegexPattern);
3382
3383 bool FormattingOff = false;
3384
3385 for (;;) {
3386 auto Pos = Code.find('\n', SearchFrom);
3387 StringRef Line =
3388 Code.substr(Prev, (Pos != StringRef::npos ? Pos : Code.size()) - Prev);
3389
3390 StringRef Trimmed = Line.trim();
3391 if (isClangFormatOff(Trimmed))
3392 FormattingOff = true;
3393 else if (isClangFormatOn(Trimmed))
3394 FormattingOff = false;
3395
3396 if (ImportRegex.match(Line, &Matches)) {
3397 if (FormattingOff) {
3398 // If at least one import line has formatting turned off, turn off
3399 // formatting entirely.
3400 return Replaces;
3401 }
3402 StringRef Static = Matches[1];
3403 StringRef Identifier = Matches[2];
3404 bool IsStatic = false;
3405 if (Static.contains("static"))
3406 IsStatic = true;
3407 ImportsInBlock.push_back(
3409 AssociatedCommentLines.clear();
3410 } else if (Trimmed.size() > 0 && !ImportsInBlock.empty()) {
3411 // Associating comments within the imports with the nearest import below
3412 AssociatedCommentLines.push_back(Line);
3413 }
3414 Prev = Pos + 1;
3415 if (Pos == StringRef::npos || Pos + 1 == Code.size())
3416 break;
3417 SearchFrom = Pos + 1;
3418 }
3419 if (!ImportsInBlock.empty())
3420 sortJavaImports(Style, ImportsInBlock, Ranges, FileName, Code, Replaces);
3421 return Replaces;
3422}
3423
3424bool isMpegTS(StringRef Code) {
3425 // MPEG transport streams use the ".ts" file extension. clang-format should
3426 // not attempt to format those. MPEG TS' frame format starts with 0x47 every
3427 // 189 bytes - detect that and return.
3428 return Code.size() > 188 && Code[0] == 0x47 && Code[188] == 0x47;
3429}
3430
3431bool isLikelyXml(StringRef Code) { return Code.ltrim().starts_with("<"); }
3432
3435 StringRef FileName, unsigned *Cursor) {
3436 tooling::Replacements Replaces;
3437 if (!Style.SortIncludes || Style.DisableFormat)
3438 return Replaces;
3439 if (isLikelyXml(Code))
3440 return Replaces;
3442 isMpegTS(Code)) {
3443 return Replaces;
3444 }
3446 return sortJavaScriptImports(Style, Code, Ranges, FileName);
3448 return sortJavaImports(Style, Code, Ranges, FileName, Replaces);
3449 sortCppIncludes(Style, Code, Ranges, FileName, Replaces, Cursor);
3450 return Replaces;
3451}
3452
3453template <typename T>
3455processReplacements(T ProcessFunc, StringRef Code,
3456 const tooling::Replacements &Replaces,
3457 const FormatStyle &Style) {
3458 if (Replaces.empty())
3459 return tooling::Replacements();
3460
3461 auto NewCode = applyAllReplacements(Code, Replaces);
3462 if (!NewCode)
3463 return NewCode.takeError();
3464 std::vector<tooling::Range> ChangedRanges = Replaces.getAffectedRanges();
3465 StringRef FileName = Replaces.begin()->getFilePath();
3466
3467 tooling::Replacements FormatReplaces =
3468 ProcessFunc(Style, *NewCode, ChangedRanges, FileName);
3469
3470 return Replaces.merge(FormatReplaces);
3471}
3472
3474formatReplacements(StringRef Code, const tooling::Replacements &Replaces,
3475 const FormatStyle &Style) {
3476 // We need to use lambda function here since there are two versions of
3477 // `sortIncludes`.
3478 auto SortIncludes = [](const FormatStyle &Style, StringRef Code,
3479 std::vector<tooling::Range> Ranges,
3480 StringRef FileName) -> tooling::Replacements {
3481 return sortIncludes(Style, Code, Ranges, FileName);
3482 };
3483 auto SortedReplaces =
3484 processReplacements(SortIncludes, Code, Replaces, Style);
3485 if (!SortedReplaces)
3486 return SortedReplaces.takeError();
3487
3488 // We need to use lambda function here since there are two versions of
3489 // `reformat`.
3490 auto Reformat = [](const FormatStyle &Style, StringRef Code,
3491 std::vector<tooling::Range> Ranges,
3492 StringRef FileName) -> tooling::Replacements {
3493 return reformat(Style, Code, Ranges, FileName);
3494 };
3495 return processReplacements(Reformat, Code, *SortedReplaces, Style);
3496}
3497
3498namespace {
3499
3500inline bool isHeaderInsertion(const tooling::Replacement &Replace) {
3501 return Replace.getOffset() == UINT_MAX && Replace.getLength() == 0 &&
3503 Replace.getReplacementText());
3504}
3505
3506inline bool isHeaderDeletion(const tooling::Replacement &Replace) {
3507 return Replace.getOffset() == UINT_MAX && Replace.getLength() == 1;
3508}
3509
3510// FIXME: insert empty lines between newly created blocks.
3511tooling::Replacements
3512fixCppIncludeInsertions(StringRef Code, const tooling::Replacements &Replaces,
3513 const FormatStyle &Style) {
3514 if (!Style.isCpp())
3515 return Replaces;
3516
3517 tooling::Replacements HeaderInsertions;
3518 std::set<llvm::StringRef> HeadersToDelete;
3519 tooling::Replacements Result;
3520 for (const auto &R : Replaces) {
3521 if (isHeaderInsertion(R)) {
3522 // Replacements from \p Replaces must be conflict-free already, so we can
3523 // simply consume the error.
3524 llvm::consumeError(HeaderInsertions.add(R));
3525 } else if (isHeaderDeletion(R)) {
3526 HeadersToDelete.insert(R.getReplacementText());
3527 } else if (R.getOffset() == UINT_MAX) {
3528 llvm::errs() << "Insertions other than header #include insertion are "
3529 "not supported! "
3530 << R.getReplacementText() << "\n";
3531 } else {
3532 llvm::consumeError(Result.add(R));
3533 }
3534 }
3535 if (HeaderInsertions.empty() && HeadersToDelete.empty())
3536 return Replaces;
3537
3538 StringRef FileName = Replaces.begin()->getFilePath();
3539 tooling::HeaderIncludes Includes(FileName, Code, Style.IncludeStyle);
3540
3541 for (const auto &Header : HeadersToDelete) {
3542 tooling::Replacements Replaces =
3543 Includes.remove(Header.trim("\"<>"), Header.starts_with("<"));
3544 for (const auto &R : Replaces) {
3545 auto Err = Result.add(R);
3546 if (Err) {
3547 // Ignore the deletion on conflict.
3548 llvm::errs() << "Failed to add header deletion replacement for "
3549 << Header << ": " << llvm::toString(std::move(Err))
3550 << "\n";
3551 }
3552 }
3553 }
3554
3556 for (const auto &R : HeaderInsertions) {
3557 auto IncludeDirective = R.getReplacementText();
3558 bool Matched =
3559 tooling::HeaderIncludes::IncludeRegex.match(IncludeDirective, &Matches);
3560 assert(Matched && "Header insertion replacement must have replacement text "
3561 "'#include ...'");
3562 (void)Matched;
3563 auto IncludeName = Matches[2];
3564 auto Replace =
3565 Includes.insert(IncludeName.trim("\"<>"), IncludeName.starts_with("<"),
3567 if (Replace) {
3568 auto Err = Result.add(*Replace);
3569 if (Err) {
3570 llvm::consumeError(std::move(Err));
3571 unsigned NewOffset =
3572 Result.getShiftedCodePosition(Replace->getOffset());
3573 auto Shifted = tooling::Replacement(FileName, NewOffset, 0,
3574 Replace->getReplacementText());
3575 Result = Result.merge(tooling::Replacements(Shifted));
3576 }
3577 }
3578 }
3579 return Result;
3580}
3581
3582} // anonymous namespace
3583
3585cleanupAroundReplacements(StringRef Code, const tooling::Replacements &Replaces,
3586 const FormatStyle &Style) {
3587 // We need to use lambda function here since there are two versions of
3588 // `cleanup`.
3589 auto Cleanup = [](const FormatStyle &Style, StringRef Code,
3591 StringRef FileName) -> tooling::Replacements {
3592 return cleanup(Style, Code, Ranges, FileName);
3593 };
3594 // Make header insertion replacements insert new headers into correct blocks.
3595 tooling::Replacements NewReplaces =
3596 fixCppIncludeInsertions(Code, Replaces, Style);
3597 return cantFail(processReplacements(Cleanup, Code, NewReplaces, Style));
3598}
3599
3600namespace internal {
3601std::pair<tooling::Replacements, unsigned>
3602reformat(const FormatStyle &Style, StringRef Code,
3603 ArrayRef<tooling::Range> Ranges, unsigned FirstStartColumn,
3604 unsigned NextStartColumn, unsigned LastStartColumn, StringRef FileName,
3605 FormattingAttemptStatus *Status) {
3606 FormatStyle Expanded = Style;
3610 Expanded.InsertBraces = false;
3611 Expanded.RemoveBracesLLVM = false;
3612 Expanded.RemoveParentheses = FormatStyle::RPS_Leave;
3613 Expanded.RemoveSemicolon = false;
3614 switch (Expanded.RequiresClausePosition) {
3615 case FormatStyle::RCPS_SingleLine:
3616 case FormatStyle::RCPS_WithPreceding:
3617 Expanded.IndentRequiresClause = false;
3618 break;
3619 default:
3620 break;
3621 }
3622
3623 if (Expanded.DisableFormat)
3624 return {tooling::Replacements(), 0};
3625 if (isLikelyXml(Code))
3626 return {tooling::Replacements(), 0};
3627 if (Expanded.Language == FormatStyle::LK_JavaScript && isMpegTS(Code))
3628 return {tooling::Replacements(), 0};
3629
3630 // JSON only needs the formatting passing.
3631 if (Style.isJson()) {
3632 std::vector<tooling::Range> Ranges(1, tooling::Range(0, Code.size()));
3633 auto Env = Environment::make(Code, FileName, Ranges, FirstStartColumn,
3634 NextStartColumn, LastStartColumn);
3635 if (!Env)
3636 return {};
3637 // Perform the actual formatting pass.
3638 tooling::Replacements Replaces =
3639 Formatter(*Env, Style, Status).process().first;
3640 // add a replacement to remove the "x = " from the result.
3641 Replaces = Replaces.merge(
3643 // apply the reformatting changes and the removal of "x = ".
3644 if (applyAllReplacements(Code, Replaces))
3645 return {Replaces, 0};
3646 return {tooling::Replacements(), 0};
3647 }
3648
3649 auto Env = Environment::make(Code, FileName, Ranges, FirstStartColumn,
3650 NextStartColumn, LastStartColumn);
3651 if (!Env)
3652 return {};
3653
3654 typedef std::function<std::pair<tooling::Replacements, unsigned>(
3655 const Environment &)>
3657
3659
3660 Passes.emplace_back([&](const Environment &Env) {
3661 return IntegerLiteralSeparatorFixer().process(Env, Expanded);
3662 });
3663
3664 if (Style.isCpp()) {
3665 if (Style.QualifierAlignment != FormatStyle::QAS_Leave)
3666 addQualifierAlignmentFixerPasses(Expanded, Passes);
3667
3668 if (Style.RemoveParentheses != FormatStyle::RPS_Leave) {
3669 FormatStyle S = Expanded;
3670 S.RemoveParentheses = Style.RemoveParentheses;
3671 Passes.emplace_back([&, S = std::move(S)](const Environment &Env) {
3672 return ParensRemover(Env, S).process(/*SkipAnnotation=*/true);
3673 });
3674 }
3675
3676 if (Style.InsertBraces) {
3677 FormatStyle S = Expanded;
3678 S.InsertBraces = true;
3679 Passes.emplace_back([&, S = std::move(S)](const Environment &Env) {
3680 return BracesInserter(Env, S).process(/*SkipAnnotation=*/true);
3681 });
3682 }
3683
3684 if (Style.RemoveBracesLLVM) {
3685 FormatStyle S = Expanded;
3686 S.RemoveBracesLLVM = true;
3687 Passes.emplace_back([&, S = std::move(S)](const Environment &Env) {
3688 return BracesRemover(Env, S).process(/*SkipAnnotation=*/true);
3689 });
3690 }
3691
3692 if (Style.RemoveSemicolon) {
3693 FormatStyle S = Expanded;
3694 S.RemoveSemicolon = true;
3695 Passes.emplace_back([&, S = std::move(S)](const Environment &Env) {
3696 return SemiRemover(Env, S).process();
3697 });
3698 }
3699
3700 if (Style.FixNamespaceComments) {
3701 Passes.emplace_back([&](const Environment &Env) {
3702 return NamespaceEndCommentsFixer(Env, Expanded).process();
3703 });
3704 }
3705
3706 if (Style.SortUsingDeclarations != FormatStyle::SUD_Never) {
3707 Passes.emplace_back([&](const Environment &Env) {
3708 return UsingDeclarationsSorter(Env, Expanded).process();
3709 });
3710 }
3711 }
3712
3713 if (Style.SeparateDefinitionBlocks != FormatStyle::SDS_Leave) {
3714 Passes.emplace_back([&](const Environment &Env) {
3715 return DefinitionBlockSeparator(Env, Expanded).process();
3716 });
3717 }
3718
3719 if (Style.Language == FormatStyle::LK_ObjC &&
3720 !Style.ObjCPropertyAttributeOrder.empty()) {
3721 Passes.emplace_back([&](const Environment &Env) {
3722 return ObjCPropertyAttributeOrderFixer(Env, Expanded).process();
3723 });
3724 }
3725
3726 if (Style.isJavaScript() &&
3727 Style.JavaScriptQuotes != FormatStyle::JSQS_Leave) {
3728 Passes.emplace_back([&](const Environment &Env) {
3729 return JavaScriptRequoter(Env, Expanded).process(/*SkipAnnotation=*/true);
3730 });
3731 }
3732
3733 Passes.emplace_back([&](const Environment &Env) {
3734 return Formatter(Env, Expanded, Status).process();
3735 });
3736
3737 if (Style.isJavaScript() &&
3738 Style.InsertTrailingCommas == FormatStyle::TCS_Wrapped) {
3739 Passes.emplace_back([&](const Environment &Env) {
3740 return TrailingCommaInserter(Env, Expanded).process();
3741 });
3742 }
3743
3744 std::optional<std::string> CurrentCode;
3746 unsigned Penalty = 0;
3747 for (size_t I = 0, E = Passes.size(); I < E; ++I) {
3748 std::pair<tooling::Replacements, unsigned> PassFixes = Passes[I](*Env);
3749 auto NewCode = applyAllReplacements(
3750 CurrentCode ? StringRef(*CurrentCode) : Code, PassFixes.first);
3751 if (NewCode) {
3752 Fixes = Fixes.merge(PassFixes.first);
3753 Penalty += PassFixes.second;
3754 if (I + 1 < E) {
3755 CurrentCode = std::move(*NewCode);
3756 Env = Environment::make(
3757 *CurrentCode, FileName,
3758 tooling::calculateRangesAfterReplacements(Fixes, Ranges),
3759 FirstStartColumn, NextStartColumn, LastStartColumn);
3760 if (!Env)
3761 return {};
3762 }
3763 }
3764 }
3765
3766 if (Style.QualifierAlignment != FormatStyle::QAS_Leave) {
3767 // Don't make replacements that replace nothing. QualifierAlignment can
3768 // produce them if one of its early passes changes e.g. `const volatile` to
3769 // `volatile const` and then a later pass changes it back again.
3770 tooling::Replacements NonNoOpFixes;
3771 for (const tooling::Replacement &Fix : Fixes) {
3772 StringRef OriginalCode = Code.substr(Fix.getOffset(), Fix.getLength());
3773 if (OriginalCode != Fix.getReplacementText()) {
3774 auto Err = NonNoOpFixes.add(Fix);
3775 if (Err) {
3776 llvm::errs() << "Error adding replacements : "
3777 << llvm::toString(std::move(Err)) << "\n";
3778 }
3779 }
3780 }
3781 Fixes = std::move(NonNoOpFixes);
3782 }
3783
3784 return {Fixes, Penalty};
3785}
3786} // namespace internal
3787
3788tooling::Replacements reformat(const FormatStyle &Style, StringRef Code,
3790 StringRef FileName,
3791 FormattingAttemptStatus *Status) {
3792 return internal::reformat(Style, Code, Ranges,
3793 /*FirstStartColumn=*/0,
3794 /*NextStartColumn=*/0,
3795 /*LastStartColumn=*/0, FileName, Status)
3796 .first;
3797}
3798
3799tooling::Replacements cleanup(const FormatStyle &Style, StringRef Code,
3801 StringRef FileName) {
3802 // cleanups only apply to C++ (they mostly concern ctor commas etc.)
3803 if (Style.Language != FormatStyle::LK_Cpp)
3804 return tooling::Replacements();
3805 auto Env = Environment::make(Code, FileName, Ranges);
3806 if (!Env)
3807 return {};
3808 return Cleaner(*Env, Style).process().first;
3809}
3810
3811tooling::Replacements reformat(const FormatStyle &Style, StringRef Code,
3813 StringRef FileName, bool *IncompleteFormat) {
3815 auto Result = reformat(Style, Code, Ranges, FileName, &Status);
3816 if (!Status.FormatComplete)
3817 *IncompleteFormat = true;
3818 return Result;
3819}
3820
3822 StringRef Code,
3824 StringRef FileName) {
3825 auto Env = Environment::make(Code, FileName, Ranges);
3826 if (!Env)
3827 return {};
3828 return NamespaceEndCommentsFixer(*Env, Style).process().first;
3829}
3830
3832 StringRef Code,
3834 StringRef FileName) {
3835 auto Env = Environment::make(Code, FileName, Ranges);
3836 if (!Env)
3837 return {};
3838 return UsingDeclarationsSorter(*Env, Style).process().first;
3839}
3840
3842 LangOptions LangOpts;
3843
3844 FormatStyle::LanguageStandard LexingStd = Style.Standard;
3845 if (LexingStd == FormatStyle::LS_Auto)
3846 LexingStd = FormatStyle::LS_Latest;
3847 if (LexingStd == FormatStyle::LS_Latest)
3848 LexingStd = FormatStyle::LS_Cpp20;
3849 LangOpts.CPlusPlus = 1;
3850 LangOpts.CPlusPlus11 = LexingStd >= FormatStyle::LS_Cpp11;
3851 LangOpts.CPlusPlus14 = LexingStd >= FormatStyle::LS_Cpp14;
3852 LangOpts.CPlusPlus17 = LexingStd >= FormatStyle::LS_Cpp17;
3853 LangOpts.CPlusPlus20 = LexingStd >= FormatStyle::LS_Cpp20;
3854 LangOpts.Char8 = LexingStd >= FormatStyle::LS_Cpp20;
3855 // Turning on digraphs in standards before C++0x is error-prone, because e.g.
3856 // the sequence "<::" will be unconditionally treated as "[:".
3857 // Cf. Lexer::LexTokenInternal.
3858 LangOpts.Digraphs = LexingStd >= FormatStyle::LS_Cpp11;
3859
3860 LangOpts.LineComment = 1;
3861 LangOpts.CXXOperatorNames = Style.isCpp();
3862 LangOpts.Bool = 1;
3863 LangOpts.ObjC = 1;
3864 LangOpts.MicrosoftExt = 1; // To get kw___try, kw___finally.
3865 LangOpts.DeclSpecKeyword = 1; // To get __declspec.
3866 LangOpts.C99 = 1; // To get kw_restrict for non-underscore-prefixed restrict.
3867 return LangOpts;
3868}
3869
3871 "Set coding style. <string> can be:\n"
3872 "1. A preset: LLVM, GNU, Google, Chromium, Microsoft,\n"
3873 " Mozilla, WebKit.\n"
3874 "2. 'file' to load style configuration from a\n"
3875 " .clang-format file in one of the parent directories\n"
3876 " of the source file (for stdin, see --assume-filename).\n"
3877 " If no .clang-format file is found, falls back to\n"
3878 " --fallback-style.\n"
3879 " --style=file is the default.\n"
3880 "3. 'file:<format_file_path>' to explicitly specify\n"
3881 " the configuration file.\n"
3882 "4. \"{key: value, ...}\" to set specific parameters, e.g.:\n"
3883 " --style=\"{BasedOnStyle: llvm, IndentWidth: 8}\"";
3884
3886 if (FileName.ends_with(".java"))
3887 return FormatStyle::LK_Java;
3888 if (FileName.ends_with_insensitive(".js") ||
3889 FileName.ends_with_insensitive(".mjs") ||
3890 FileName.ends_with_insensitive(".ts")) {
3891 return FormatStyle::LK_JavaScript; // (module) JavaScript or TypeScript.
3892 }
3893 if (FileName.ends_with(".m") || FileName.ends_with(".mm"))
3894 return FormatStyle::LK_ObjC;
3895 if (FileName.ends_with_insensitive(".proto") ||
3896 FileName.ends_with_insensitive(".protodevel")) {
3897 return FormatStyle::LK_Proto;
3898 }
3899 // txtpb is the canonical extension, and textproto is the legacy canonical
3900 // extension
3901 // https://protobuf.dev/reference/protobuf/textformat-spec/#text-format-files
3902 if (FileName.ends_with_insensitive(".txtpb") ||
3903 FileName.ends_with_insensitive(".textpb") ||
3904 FileName.ends_with_insensitive(".pb.txt") ||
3905 FileName.ends_with_insensitive(".textproto") ||
3906 FileName.ends_with_insensitive(".asciipb")) {
3908 }
3909 if (FileName.ends_with_insensitive(".td"))
3911 if (FileName.ends_with_insensitive(".cs"))
3913 if (FileName.ends_with_insensitive(".json"))
3914 return FormatStyle::LK_Json;
3915 if (FileName.ends_with_insensitive(".sv") ||
3916 FileName.ends_with_insensitive(".svh") ||
3917 FileName.ends_with_insensitive(".v") ||
3918 FileName.ends_with_insensitive(".vh")) {
3920 }
3921 return FormatStyle::LK_Cpp;
3922}
3923
3925 const auto GuessedLanguage = getLanguageByFileName(FileName);
3926 if (GuessedLanguage == FormatStyle::LK_Cpp) {
3927 auto Extension = llvm::sys::path::extension(FileName);
3928 // If there's no file extension (or it's .h), we need to check the contents
3929 // of the code to see if it contains Objective-C.
3930 if (!Code.empty() && (Extension.empty() || Extension == ".h")) {
3931 auto NonEmptyFileName = FileName.empty() ? "guess.h" : FileName;
3932 Environment Env(Code, NonEmptyFileName, /*Ranges=*/{});
3933 ObjCHeaderStyleGuesser Guesser(Env, getLLVMStyle());
3934 Guesser.process();
3935 if (Guesser.isObjC())
3936 return FormatStyle::LK_ObjC;
3937 }
3938 }
3939 return GuessedLanguage;
3940}
3941
3942// Update StyleOptionHelpDescription above when changing this.
3943const char *DefaultFormatStyle = "file";
3944
3945const char *DefaultFallbackStyle = "LLVM";
3946
3947llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>>
3948loadAndParseConfigFile(StringRef ConfigFile, llvm::vfs::FileSystem *FS,
3949 FormatStyle *Style, bool AllowUnknownOptions) {
3950 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> Text =
3951 FS->getBufferForFile(ConfigFile.str());
3952 if (auto EC = Text.getError())
3953 return EC;
3954 if (auto EC = parseConfiguration(*Text.get(), Style, AllowUnknownOptions))
3955 return EC;
3956 return Text;
3957}
3958
3959llvm::Expected<FormatStyle> getStyle(StringRef StyleName, StringRef FileName,
3960 StringRef FallbackStyleName,
3961 StringRef Code, llvm::vfs::FileSystem *FS,
3962 bool AllowUnknownOptions) {
3964 FormatStyle FallbackStyle = getNoStyle();
3965 if (!getPredefinedStyle(FallbackStyleName, Style.Language, &FallbackStyle))
3966 return make_string_error("Invalid fallback style: " + FallbackStyleName);
3967
3969 ChildFormatTextToApply;
3970
3971 if (StyleName.starts_with("{")) {
3972 // Parse YAML/JSON style from the command line.
3973 StringRef Source = "<command-line>";
3974 if (std::error_code ec =
3975 parseConfiguration(llvm::MemoryBufferRef(StyleName, Source), &Style,
3976 AllowUnknownOptions)) {
3977 return make_string_error("Error parsing -style: " + ec.message());
3978 }
3979
3980 if (!Style.InheritsParentConfig)
3981 return Style;
3982
3983 ChildFormatTextToApply.emplace_back(
3984 llvm::MemoryBuffer::getMemBuffer(StyleName, Source, false));
3985 }
3986
3987 if (!FS)
3988 FS = llvm::vfs::getRealFileSystem().get();
3989 assert(FS);
3990
3991 // User provided clang-format file using -style=file:path/to/format/file.
3992 if (!Style.InheritsParentConfig &&
3993 StyleName.starts_with_insensitive("file:")) {
3994 auto ConfigFile = StyleName.substr(5);
3995 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> Text =
3996 loadAndParseConfigFile(ConfigFile, FS, &Style, AllowUnknownOptions);
3997 if (auto EC = Text.getError()) {
3998 return make_string_error("Error reading " + ConfigFile + ": " +
3999 EC.message());
4000 }
4001
4002 LLVM_DEBUG(llvm::dbgs()
4003 << "Using configuration file " << ConfigFile << "\n");
4004
4005 if (!Style.InheritsParentConfig)
4006 return Style;
4007
4008 // Search for parent configs starting from the parent directory of
4009 // ConfigFile.
4010 FileName = ConfigFile;
4011 ChildFormatTextToApply.emplace_back(std::move(*Text));
4012 }
4013
4014 // If the style inherits the parent configuration it is a command line
4015 // configuration, which wants to inherit, so we have to skip the check of the
4016 // StyleName.
4017 if (!Style.InheritsParentConfig && !StyleName.equals_insensitive("file")) {
4018 if (!getPredefinedStyle(StyleName, Style.Language, &Style))
4019 return make_string_error("Invalid value for -style");
4020 if (!Style.InheritsParentConfig)
4021 return Style;
4022 }
4023
4025 if (std::error_code EC = FS->makeAbsolute(Path))
4026 return make_string_error(EC.message());
4027
4028 // Reset possible inheritance
4029 Style.InheritsParentConfig = false;
4030
4031 auto dropDiagnosticHandler = [](const llvm::SMDiagnostic &, void *) {};
4032
4033 auto applyChildFormatTexts = [&](FormatStyle *Style) {
4034 for (const auto &MemBuf : llvm::reverse(ChildFormatTextToApply)) {
4035 auto EC = parseConfiguration(*MemBuf, Style, AllowUnknownOptions,
4036 dropDiagnosticHandler);
4037 // It was already correctly parsed.
4038 assert(!EC);
4039 static_cast<void>(EC);
4040 }
4041 };
4042
4043 // Look for .clang-format/_clang-format file in the file's parent directories.
4044 llvm::SmallVector<std::string, 2> FilesToLookFor;
4045 FilesToLookFor.push_back(".clang-format");
4046 FilesToLookFor.push_back("_clang-format");
4047
4048 SmallString<128> UnsuitableConfigFiles;
4049 for (StringRef Directory = Path; !Directory.empty();
4050 Directory = llvm::sys::path::parent_path(Directory)) {
4051 auto Status = FS->status(Directory);
4052 if (!Status ||
4053 Status->getType() != llvm::sys::fs::file_type::directory_file) {
4054 continue;
4055 }
4056
4057 for (const auto &F : FilesToLookFor) {
4058 SmallString<128> ConfigFile(Directory);
4059
4060 llvm::sys::path::append(ConfigFile, F);
4061 LLVM_DEBUG(llvm::dbgs() << "Trying " << ConfigFile << "...\n");
4062
4063 Status = FS->status(ConfigFile);
4064 if (!Status ||
4065 Status->getType() != llvm::sys::fs::file_type::regular_file) {
4066 continue;
4067 }
4068
4069 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> Text =
4070 loadAndParseConfigFile(ConfigFile, FS, &Style, AllowUnknownOptions);
4071 if (auto EC = Text.getError()) {
4072 if (EC != ParseError::Unsuitable) {
4073 return make_string_error("Error reading " + ConfigFile + ": " +
4074 EC.message());
4075 }
4076 if (!UnsuitableConfigFiles.empty())
4077 UnsuitableConfigFiles.append(", ");
4078 UnsuitableConfigFiles.append(ConfigFile);
4079 continue;
4080 }
4081
4082 LLVM_DEBUG(llvm::dbgs()
4083 << "Using configuration file " << ConfigFile << "\n");
4084
4085 if (!Style.InheritsParentConfig) {
4086 if (!ChildFormatTextToApply.empty()) {
4087 LLVM_DEBUG(llvm::dbgs() << "Applying child configurations\n");
4088 applyChildFormatTexts(&Style);
4089 }
4090 return Style;
4091 }
4092
4093 LLVM_DEBUG(llvm::dbgs() << "Inherits parent configuration\n");
4094
4095 // Reset inheritance of style
4096 Style.InheritsParentConfig = false;
4097
4098 ChildFormatTextToApply.emplace_back(std::move(*Text));
4099
4100 // Breaking out of the inner loop, since we don't want to parse
4101 // .clang-format AND _clang-format, if both exist. Then we continue the
4102 // outer loop (parent directories) in search for the parent
4103 // configuration.
4104 break;
4105 }
4106 }
4107
4108 if (!UnsuitableConfigFiles.empty()) {
4109 return make_string_error("Configuration file(s) do(es) not support " +
4110 getLanguageName(Style.Language) + ": " +
4111 UnsuitableConfigFiles);
4112 }
4113
4114 if (!ChildFormatTextToApply.empty()) {
4115 LLVM_DEBUG(llvm::dbgs()
4116 << "Applying child configurations on fallback style\n");
4117 applyChildFormatTexts(&FallbackStyle);
4118 }
4119
4120 return FallbackStyle;
4121}
4122
4123static bool isClangFormatOnOff(StringRef Comment, bool On) {
4124 if (Comment == (On ? "/* clang-format on */" : "/* clang-format off */"))
4125 return true;
4126
4127 static const char ClangFormatOn[] = "// clang-format on";
4128 static const char ClangFormatOff[] = "// clang-format off";
4129 const unsigned Size = (On ? sizeof ClangFormatOn : sizeof ClangFormatOff) - 1;
4130
4131 return Comment.starts_with(On ? ClangFormatOn : ClangFormatOff) &&
4132 (Comment.size() == Size || Comment[Size] == ':');
4133}
4134
4135bool isClangFormatOn(StringRef Comment) {
4136 return isClangFormatOnOff(Comment, /*On=*/true);
4137}
4138
4139bool isClangFormatOff(StringRef Comment) {
4140 return isClangFormatOnOff(Comment, /*On=*/false);
4141}
4142
4143} // namespace format
4144} // namespace clang
#define SM(sm)
Definition: Cuda.cpp:83
This file declares DefinitionBlockSeparator, a TokenAnalyzer that inserts or removes empty lines sepa...
StringRef Text
Definition: Format.cpp:2976
int Priority
Definition: Format.cpp:2979
SmallVector< StringRef > AssociatedCommentLines
Definition: Format.cpp:2986
int Category
Definition: Format.cpp:2978
bool IsStatic
Definition: Format.cpp:2987
StringRef Filename
Definition: Format.cpp:2975
StringRef Identifier
Definition: Format.cpp:2983
Various functions to configurably format source code.
const Environment & Env
Definition: HTMLLogger.cpp:148
This file declares IntegerLiteralSeparatorFixer that fixes C++ integer literal separators.
This file declares NamespaceEndCommentsFixer, a TokenAnalyzer that fixes namespace end comments.
This file declares ObjCPropertyAttributeOrderFixer, a TokenAnalyzer that adjusts the order of attribu...
This file declares QualifierAlignmentFixer, a TokenAnalyzer that enforces either east or west const d...
SourceRange Range
Definition: SemaObjC.cpp:754
This file implements a sorter for JavaScript ES6 imports.
ContinuationIndenter * Indenter
Implements a combinatorial exploration of all the different linebreaks unwrapped lines can be formatt...
This file declares UsingDeclarationsSorter, a TokenAnalyzer that sorts consecutive using declarations...
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:461
static std::unique_ptr< Environment > make(StringRef Code, StringRef FileName, ArrayRef< tooling::Range > Ranges, unsigned FirstStartColumn=0, unsigned NextStartColumn=0, unsigned LastStartColumn=0)
std::pair< tooling::Replacements, unsigned > process(const Environment &Env, const FormatStyle &Style)
static tok::TokenKind getTokenFromQualifier(const std::string &Qualifier)
const char * name() const noexcept override
Definition: Format.cpp:1243
std::string message(int EV) const override
Definition: Format.cpp:1247
std::pair< tooling::Replacements, unsigned > process(bool SkipAnnotation=false)
static const llvm::Regex IncludeRegex
This class manages priorities of C++ #include categories and calculates priorities for headers.
int getIncludePriority(StringRef IncludeName, bool CheckMainHeader) const
Returns the priority of the category which IncludeName belongs to.
int getSortIncludePriority(StringRef IncludeName, bool CheckMainHeader) const
A source range independent of the SourceManager.
Definition: Replacement.h:44
A text replacement.
Definition: Replacement.h:83
unsigned getLength() const
Definition: Replacement.h:122
StringRef getReplacementText() const
Definition: Replacement.h:123
unsigned getOffset() const
Definition: Replacement.h:121
Maintains a set of replacements that are conflict-free.
Definition: Replacement.h:212
std::vector< Range > getAffectedRanges() const
const_iterator begin() const
Definition: Replacement.h:281
llvm::Error add(const Replacement &R)
Adds a new replacement R to the current set of replacements.
Replacements merge(const Replacements &Replaces) const
Merges Replaces into the current replacements.
#define UINT_MAX
Definition: limits.h:64
SmallVector< BoundNodes, 1 > match(MatcherT Matcher, const NodeT &Node, ASTContext &Context)
Returns the results of matching Matcher on Node.
bool isObjC(ID Id)
isObjC - Is this an "ObjC" input (Obj-C and Obj-C++ sources and headers).
Definition: Types.cpp:217
std::pair< tooling::Replacements, unsigned > reformat(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, unsigned FirstStartColumn, unsigned NextStartColumn, unsigned LastStartColumn, StringRef FileName, FormattingAttemptStatus *Status)
Reformats the given Ranges in the code fragment Code.
Definition: Format.cpp:3602
const char * StyleOptionHelpDescription
Description to be used for help text for a llvm::cl option for specifying format style.
Definition: Format.cpp:3870
void addQualifierAlignmentFixerPasses(const FormatStyle &Style, SmallVectorImpl< AnalyzerPass > &Passes)
static void expandPresetsSpaceBeforeParens(FormatStyle &Expanded)
Definition: Format.cpp:1369
const char * DefaultFallbackStyle
The suggested predefined style to use as the fallback style in getStyle.
Definition: Format.cpp:3945
static bool affectsRange(ArrayRef< tooling::Range > Ranges, unsigned Start, unsigned End)
Definition: Format.cpp:2993
const char * getTokenTypeName(TokenType Type)
Determines the name of a token type.
Definition: FormatToken.cpp:24
FormatStyle getWebKitStyle()
Returns a format style complying with Webkit's style guide: http://www.webkit.org/coding/coding-style...
Definition: Format.cpp:1846
bool isLikelyXml(StringRef Code)
Definition: Format.cpp:3431
static FormatStyle::LanguageKind getLanguageByFileName(StringRef FileName)
Definition: Format.cpp:3885
llvm::Error make_string_error(const llvm::Twine &Message)
Definition: Format.cpp:1238
static unsigned findJavaImportGroup(const FormatStyle &Style, StringRef ImportIdentifier)
Definition: Format.cpp:3270
llvm::Expected< tooling::Replacements > cleanupAroundReplacements(StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Returns the replacements corresponding to applying Replaces and cleaning up the code after that on su...
Definition: Format.cpp:3585
std::string replaceCRLF(const std::string &Code)
Definition: Format.cpp:3033
static std::pair< unsigned, unsigned > FindCursorIndex(const SmallVectorImpl< IncludeDirective > &Includes, const SmallVectorImpl< unsigned > &Indices, unsigned Cursor)
Definition: Format.cpp:3012
std::error_code make_error_code(ParseError e)
Definition: Format.cpp:1234
FormatStyle getClangFormatStyle()
Definition: Format.cpp:1914
std::function< std::pair< tooling::Replacements, unsigned >(const Environment &)> AnalyzerPass
FormatStyle getLLVMStyle(FormatStyle::LanguageKind Language=FormatStyle::LanguageKind::LK_Cpp)
Returns a format style complying with the LLVM coding standards: http://llvm.org/docs/CodingStandards...
Definition: Format.cpp:1401
static llvm::Expected< tooling::Replacements > processReplacements(T ProcessFunc, StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Definition: Format.cpp:3455
FormatStyle getGoogleStyle(FormatStyle::LanguageKind Language)
Returns a format style complying with one of Google's style guides: http://google-styleguide....
Definition: Format.cpp:1618
std::string configurationAsText(const FormatStyle &Style)
Gets configuration in a YAML string.
Definition: Format.cpp:2062
FormatStyle getMicrosoftStyle(FormatStyle::LanguageKind Language)
Returns a format style complying with Microsoft style guide: https://docs.microsoft....
Definition: Format.cpp:1885
std::error_code parseConfiguration(llvm::MemoryBufferRef Config, FormatStyle *Style, bool AllowUnknownOptions=false, llvm::SourceMgr::DiagHandlerTy DiagHandler=nullptr, void *DiagHandlerCtx=nullptr)
Parse configuration from YAML-formatted text.
Definition: Format.cpp:1996
const std::error_category & getParseCategory()
Definition: Format.cpp:1230
llvm::ErrorOr< std::unique_ptr< llvm::MemoryBuffer > > loadAndParseConfigFile(StringRef ConfigFile, llvm::vfs::FileSystem *FS, FormatStyle *Style, bool AllowUnknownOptions)
Definition: Format.cpp:3948
tooling::Replacements fixNamespaceEndComments(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Fix namespace end comments in the given Ranges in Code.
Definition: Format.cpp:3821
FormatStyle::LanguageKind guessLanguage(StringRef FileName, StringRef Code)
Definition: Format.cpp:3924
bool isMpegTS(StringRef Code)
Definition: Format.cpp:3424
const char * DefaultFormatStyle
The suggested format style to use by default.
Definition: Format.cpp:3943
llvm::Expected< FormatStyle > getStyle(StringRef StyleName, StringRef FileName, StringRef FallbackStyle, StringRef Code="", llvm::vfs::FileSystem *FS=nullptr, bool AllowUnknownOptions=false)
Construct a FormatStyle based on StyleName.
Definition: Format.cpp:3959
FormatStyle getGNUStyle()
Returns a format style complying with GNU Coding Standards: http://www.gnu.org/prep/standards/standar...
Definition: Format.cpp:1870
bool isClangFormatOff(StringRef Comment)
Definition: Format.cpp:4139
LangOptions getFormattingLangOpts(const FormatStyle &Style=getLLVMStyle())
Returns the LangOpts that the formatter expects you to set.
Definition: Format.cpp:3841
static bool isClangFormatOnOff(StringRef Comment, bool On)
Definition: Format.cpp:4123
tooling::Replacements sortJavaScriptImports(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName)
FormatStyle getMozillaStyle()
Returns a format style complying with Mozilla's style guide: https://firefox-source-docs....
Definition: Format.cpp:1820
bool getPredefinedStyle(StringRef Name, FormatStyle::LanguageKind Language, FormatStyle *Style)
Gets a predefined style for the specified language by name.
Definition: Format.cpp:1935
static void expandPresetsBraceWrapping(FormatStyle &Expanded)
Definition: Format.cpp:1269
static void sortJavaImports(const FormatStyle &Style, const SmallVectorImpl< JavaImportDirective > &Imports, ArrayRef< tooling::Range > Ranges, StringRef FileName, StringRef Code, tooling::Replacements &Replaces)
Definition: Format.cpp:3290
tooling::Replacements reformat(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>", FormattingAttemptStatus *Status=nullptr)
Reformats the given Ranges in Code.
Definition: Format.cpp:3788
bool isClangFormatOn(StringRef Comment)
Definition: Format.cpp:4135
tooling::Replacements sortUsingDeclarations(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Sort consecutive using declarations in the given Ranges in Code.
Definition: Format.cpp:3831
ParseError validateQualifierOrder(FormatStyle *Style)
Definition: Format.cpp:1964
FormatStyle getChromiumStyle(FormatStyle::LanguageKind Language)
Returns a format style complying with Chromium's style guide: http://www.chromium....
Definition: Format.cpp:1760
static void expandPresetsSpacesInParens(FormatStyle &Expanded)
Definition: Format.cpp:1393
tooling::Replacements cleanup(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Clean up any erroneous/redundant code in the given Ranges in Code.
Definition: Format.cpp:3799
FormatStyle getNoStyle()
Returns style indicating formatting should be not applied at all.
Definition: Format.cpp:1927
tooling::Replacements sortIncludes(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName, unsigned *Cursor=nullptr)
Returns the replacements necessary to sort all #include blocks that are affected by Ranges.
Definition: Format.cpp:3433
static void sortCppIncludes(const FormatStyle &Style, const SmallVectorImpl< IncludeDirective > &Includes, ArrayRef< tooling::Range > Ranges, StringRef FileName, StringRef Code, tooling::Replacements &Replaces, unsigned *Cursor)
Definition: Format.cpp:3061
llvm::Expected< tooling::Replacements > formatReplacements(StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Returns the replacements corresponding to applying and formatting Replaces on success; otheriwse,...
Definition: Format.cpp:3474
StringRef getLanguageName(FormatStyle::LanguageKind Language)
Definition: Format.h:5395
The JSON file list parser is used to communicate input to InstallAPI.
Language
The language for the input, used to select and validate the language standard and possible actions.
Definition: LangStandard.h:23
@ Result
The result type of a method or function.
const FunctionProtoType * T
Diagnostic wrappers for TextAPI types for error reporting.
Definition: Dominators.h:30
Definition: Format.h:5428
bool AcrossEmptyLines
Whether to align across empty lines.
Definition: Format.h:202
bool PadOperators
Only for AlignConsecutiveAssignments.
Definition: Format.h:262
bool AlignFunctionPointers
Only for AlignConsecutiveDeclarations.
Definition: Format.h:243
bool Enabled
Whether aligning is enabled.
Definition: Format.h:185
bool AlignCompound
Only for AlignConsecutiveAssignments.
Definition: Format.h:227
bool AcrossComments
Whether to align across comments.
Definition: Format.h:215
bool SplitEmptyRecord
If false, empty record (e.g.
Definition: Format.h:1517
bool AfterClass
Wrap class definitions.
Definition: Format.h:1333
bool AfterStruct
Wrap struct definitions.
Definition: Format.h:1400
bool AfterUnion
Wrap union definitions.
Definition: Format.h:1414
bool AfterEnum
Wrap enum definitions.
Definition: Format.h:1348
bool AfterObjCDeclaration
Wrap ObjC definitions (interfaces, implementations...).
Definition: Format.h:1386
bool AfterNamespace
Wrap namespace definitions.
Definition: Format.h:1380
BraceWrappingAfterControlStatementStyle AfterControlStatement
Wrap control statements (if/for/while/switch/..).
Definition: Format.h:1336
bool AfterFunction
Wrap function definitions.
Definition: Format.h:1364
bool SplitEmptyFunction
If false, empty function body can be put on a single line.
Definition: Format.h:1505
bool AfterExternBlock
Wrap extern blocks.
Definition: Format.h:1428
std::optional< FormatStyle > Get(FormatStyle::LanguageKind Language) const
Definition: Format.cpp:2078
int8_t DecimalMinDigits
Format separators in decimal literals with a minimum number of digits.
Definition: Format.h:2985
int8_t Decimal
Format separators in decimal literals.
Definition: Format.h:2977
See documentation of RawStringFormats.
Definition: Format.h:3661
bool AfterControlStatements
If true, put space between control statement keywords (for/if/while...) and opening parentheses.
Definition: Format.h:4359
bool AfterForeachMacros
If true, put space between foreach macros and opening parentheses.
Definition: Format.h:4366
bool BeforeNonEmptyParentheses
If true, put a space before opening parentheses only if the parentheses are not empty.
Definition: Format.h:4430
bool AfterIfMacros
If true, put space between if macros and opening parentheses.
Definition: Format.h:4387
bool AfterPlacementOperator
If true, put a space between operator new/delete and opening parenthesis.
Definition: Format.h:4403
bool Other
Put a space in parentheses not covered by preceding options.
Definition: Format.h:4681
bool InEmptyParentheses
Put a space in parentheses only if the parentheses are empty i.e.
Definition: Format.h:4675
bool InCStyleCasts
Put a space in C style casts.
Definition: Format.h:4664
bool InConditionalStatements
Put a space in parentheses only inside conditional statements (for/if/while/switch....
Definition: Format.h:4658
TrailingCommentsAlignmentKinds Kind
Specifies the way to align trailing comments.
Definition: Format.h:579
unsigned OverEmptyLines
How many empty lines to apply alignment.
Definition: Format.h:602
The FormatStyle is used to configure the formatting to follow specific guidelines.
Definition: Format.h:55
@ UT_Never
Never use tab.
Definition: Format.h:4884
bool SpaceBeforeInheritanceColon
If false, spaces will be removed before inheritance colon.
Definition: Format.h:4270
unsigned ContinuationIndentWidth
Indent width for line continuations.
Definition: Format.h:2430
bool AlwaysBreakBeforeMultilineStrings
This option is renamed to BreakAfterReturnType.
Definition: Format.h:1098
LanguageStandard Standard
Parse and format C++ constructs compatible with this standard.
Definition: Format.h:4762
bool BreakAdjacentStringLiterals
Break between adjacent string literals.
Definition: Format.h:1558
ReturnTypeBreakingStyle BreakAfterReturnType
The function declaration return type breaking style to use.
Definition: Format.h:1649
LanguageKind
Supported languages.
Definition: Format.h:3146
@ LK_CSharp
Should be used for C#.
Definition: Format.h:3152
@ LK_None
Do not use.
Definition: Format.h:3148
@ LK_Java
Should be used for Java.
Definition: Format.h:3154
@ LK_Cpp
Should be used for C, C++.
Definition: Format.h:3150
@ LK_JavaScript
Should be used for JavaScript.
Definition: Format.h:3156
@ LK_ObjC
Should be used for Objective-C, Objective-C++.
Definition: Format.h:3160
@ LK_Verilog
Should be used for Verilog and SystemVerilog.
Definition: Format.h:3172
@ LK_TableGen
Should be used for TableGen code.
Definition: Format.h:3165
@ LK_Proto
Should be used for Protocol Buffers (https://developers.google.com/protocol-buffers/).
Definition: Format.h:3163
@ LK_Json
Should be used for JSON.
Definition: Format.h:3158
@ LK_TextProto
Should be used for Protocol Buffer messages in text format (https://developers.google....
Definition: Format.h:3168
bool Cpp11BracedListStyle
If true, format braced lists as best suited for C++11 braced lists.
Definition: Format.h:2453
SortIncludesOptions SortIncludes
Controls if and how clang-format will sort #includes.
Definition: Format.h:4097
BreakInheritanceListStyle BreakInheritanceList
The inheritance list style to use.
Definition: Format.h:2381
unsigned IndentWidth
The number of columns to use for indentation.
Definition: Format.h:2853
std::vector< std::string > AttributeMacros
This option is renamed to BreakTemplateDeclarations.
Definition: Format.h:1168
@ SLS_All
Merge all lambdas fitting on a single line.
Definition: Format.h:956
@ SLS_Empty
Only merge empty lambdas.
Definition: Format.h:942
@ SDS_Leave
Leave definition blocks as they are.
Definition: Format.h:3983
bool IndentRequiresClause
Indent the requires clause in a template.
Definition: Format.h:2839
SpacesInAnglesStyle SpacesInAngles
The SpacesInAnglesStyle to use for template argument lists.
Definition: Format.h:4545
bool IndentCaseLabels
Indent case labels one level from the switch statement.
Definition: Format.h:2725
std::vector< RawStringFormat > RawStringFormats
Defines hints for detecting supported languages code blocks in raw strings.
Definition: Format.h:3718
@ SJSIO_Before
Static imports are placed before non-static imports.
Definition: Format.h:4107
@ SJSIO_After
Static imports are placed after non-static imports.
Definition: Format.h:4114
PPDirectiveIndentStyle IndentPPDirectives
The preprocessor directive indenting style to use.
Definition: Format.h:2817
bool RemoveSemicolon
Remove semicolons after the closing braces of functions and constructors/destructors.
Definition: Format.h:3871
std::vector< std::string > Macros
A list of macros of the form <definition>=<expansion> .
Definition: Format.h:3275
bool SpaceBeforeJsonColon
If true, a space will be added before a JSON colon.
Definition: Format.h:4281
@ TCS_None
Do not insert trailing commas.
Definition: Format.h:2908
unsigned PenaltyBreakBeforeFirstCallParameter
The penalty for breaking a function call after call(.
Definition: Format.h:3511
bool SpaceBeforeCtorInitializerColon
If false, spaces will be removed before constructor initializer colon.
Definition: Format.h:4262
BinaryOperatorStyle BreakBeforeBinaryOperators
The way to wrap binary operators.
Definition: Format.h:1723
@ SI_Never
Includes are never sorted.
Definition: Format.h:4074
@ SI_CaseSensitive
Includes are sorted in an ASCIIbetical or case sensitive fashion.
Definition: Format.h:4083
@ SI_CaseInsensitive
Includes are sorted in an alphabetical or case insensitive fashion.
Definition: Format.h:4092
@ BPS_Never
Never bin-pack parameters.
Definition: Format.h:1678
@ BPS_Auto
Automatically determine parameter bin-packing behavior.
Definition: Format.h:1674
BitFieldColonSpacingStyle BitFieldColonSpacing
The BitFieldColonSpacingStyle to use for bitfields.
Definition: Format.h:1231
@ ELBAMS_LogicalBlock
Add empty line only when access modifier starts a new logical block.
Definition: Format.h:2559
unsigned SpacesBeforeTrailingComments
If true, spaces may be inserted into ().
Definition: Format.h:4522
@ BCIS_BeforeColon
Break constructor initializers before the colon and after the commas.
Definition: Format.h:2236
@ BCIS_BeforeComma
Break constructor initializers before the colon and commas, and align the commas with the colon.
Definition: Format.h:2244
@ IEBS_AfterExternBlock
Backwards compatible with AfterExternBlock's indenting.
Definition: Format.h:2763
bool IndentCaseBlocks
Indent case label blocks one level from the case label.
Definition: Format.h:2706
bool InsertBraces
Insert braces after control statements (if, else, for, do, and while) in C++ unless the control state...
Definition: Format.h:2899
BreakBeforeConceptDeclarationsStyle BreakBeforeConceptDeclarations
The concept declaration style to use.
Definition: Format.h:2182
BreakTemplateDeclarationsStyle BreakTemplateDeclarations
The template declaration breaking style to use.
Definition: Format.h:2385
bool DerivePointerAlignment
This option is deprecated.
Definition: Format.h:2466
@ BOS_All
Break before operators.
Definition: Format.h:1718
@ BOS_None
Break after operators.
Definition: Format.h:1694
@ BOS_NonAssignment
Break before operators that aren't assignments.
Definition: Format.h:1706
@ LE_DeriveLF
Use \n unless the input has more lines ending in \r\n.
Definition: Format.h:3195
bool SpacesInSquareBrackets
If true, spaces will be inserted after [ and before ].
Definition: Format.h:4727
bool IndentWrappedFunctionNames
Indent if a function definition or declaration is wrapped after the type.
Definition: Format.h:2867
AlignConsecutiveStyle AlignConsecutiveTableGenBreakingDAGArgColons
Style of aligning consecutive TableGen DAGArg operator colons.
Definition: Format.h:449
bool FixNamespaceComments
If true, clang-format adds missing namespace end comments for namespaces and fixes invalid existing o...
Definition: Format.h:2615
bool ObjCSpaceBeforeProtocolList
Add a space in front of an Objective-C protocol list, i.e.
Definition: Format.h:3441
@ TCAS_Never
Don't align trailing comments but other formatter applies.
Definition: Format.h:573
@ TCAS_Always
Align trailing comments.
Definition: Format.h:564
RemoveParenthesesStyle RemoveParentheses
Remove redundant parentheses.
Definition: Format.h:3853
std::string MacroBlockBegin
A regular expression matching macros that start a block.
Definition: Format.h:3231
bool SpaceInEmptyBlock
If true, spaces will be inserted into {}.
Definition: Format.h:4496
LanguageKind Language
Language, this format style is targeted at.
Definition: Format.h:3186
@ SIPO_Custom
Configure each individual space in parentheses in SpacesInParensOptions.
Definition: Format.h:4626
@ SIPO_Never
Never put a space in parentheses.
Definition: Format.h:4623
bool RemoveBracesLLVM
Remove optional braces of control statements (if, else, for, and while) in C++ according to the LLVM ...
Definition: Format.h:3817
@ BAS_DontAlign
Don't align, instead use ContinuationIndentWidth, e.g.:
Definition: Format.h:78
@ BAS_AlwaysBreak
Always break after an open bracket, if the parameters don't fit on a single line, e....
Definition: Format.h:85
@ BAS_Align
Align parameters on the open bracket, e.g.:
Definition: Format.h:72
@ BBIAS_OnlyMultiline
Break before inline ASM colon if the line length is longer than column limit.
Definition: Format.h:2199
bool VerilogBreakBetweenInstancePorts
For Verilog, put each port on its own line in module instantiations.
Definition: Format.h:4914
unsigned TabWidth
The number of columns used for tab stops.
Definition: Format.h:4848
@ PPDIS_None
Does not indent any directives.
Definition: Format.h:2794
@ LBI_Signature
Align lambda body relative to the lambda signature.
Definition: Format.h:3116
std::vector< std::string > JavaImportGroups
A vector of prefixes ordered by the desired groups for Java imports.
Definition: Format.h:3046
bool AllowShortCaseLabelsOnASingleLine
If true, short case labels will be contracted to a single line.
Definition: Format.h:771
unsigned PenaltyBreakFirstLessLess
The penalty for breaking before the first <<.
Definition: Format.h:3519
std::vector< std::string > StatementAttributeLikeMacros
Macros which are ignored in front of a statement, as if they were an attribute.
Definition: Format.h:4779
unsigned ObjCBlockIndentWidth
The number of characters to use for indentation of ObjC blocks.
Definition: Format.h:3384
bool AllowShortLoopsOnASingleLine
If true, while (true) continue; can be put on a single line.
Definition: Format.h:967
int AccessModifierOffset
The extra indent or outdent of access modifiers, e.g.
Definition: Format.h:63
std::vector< std::string > QualifierOrder
The order in which the qualifiers appear.
Definition: Format.h:3658
bool AllowShortEnumsOnASingleLine
Allow short enums on a single line.
Definition: Format.h:804
@ SBS_Empty
Only merge empty blocks.
Definition: Format.h:732
@ SBS_Never
Never merge blocks into a single line.
Definition: Format.h:724
std::optional< FormatStyle > GetLanguageStyle(LanguageKind Language) const
Definition: Format.cpp:2103
std::vector< std::string > IfMacros
A vector of macros that should be interpreted as conditionals instead of as function calls.
Definition: Format.h:2656
NamespaceIndentationKind NamespaceIndentation
The indentation used for namespaces.
Definition: Format.h:3327
bool BreakArrays
If true, clang-format will always break after a Json array [ otherwise it will scan until the closing...
Definition: Format.h:1668
bool BreakAfterJavaFieldAnnotations
Break after each annotation on a field in Java files.
Definition: Format.h:2280
@ SIS_WithoutElse
Put short ifs on the same line only if there is no else statement.
Definition: Format.h:893
@ SIS_Never
Never put short ifs on the same line.
Definition: Format.h:877
std::optional< unsigned > BracedInitializerIndentWidth
The number of columns to use to indent the contents of braced init lists.
Definition: Format.h:1264
std::vector< std::string > ObjCPropertyAttributeOrder
The order in which ObjC property attributes should appear.
Definition: Format.h:3431
bool ExperimentalAutoDetectBinPacking
If true, clang-format detects whether function calls and definitions are formatted with one parameter...
Definition: Format.h:2599
bool ObjCBreakBeforeNestedBlockParam
Break parameters list into lines when there is nested block parameters in a function call.
Definition: Format.h:3408
OperandAlignmentStyle AlignOperands
If true, horizontally align operands of binary and ternary expressions.
Definition: Format.h:543
unsigned PenaltyBreakOpenParenthesis
The penalty for breaking after (.
Definition: Format.h:3523
@ BTDS_MultiLine
Force break after template declaration only when the following declaration spans multiple lines.
Definition: Format.h:1132
@ BTDS_Yes
Always break after template declaration.
Definition: Format.h:1143
bool AllowShortCompoundRequirementOnASingleLine
Allow short compound requirement on a single line.
Definition: Format.h:790
friend std::error_code parseConfiguration(llvm::MemoryBufferRef Config, FormatStyle *Style, bool AllowUnknownOptions, llvm::SourceMgr::DiagHandlerTy DiagHandler, void *DiagHandlerCtxt)
Parse configuration from YAML-formatted text.
Definition: Format.cpp:1996
SpacesInParensStyle SpacesInParens
If true, spaces will be inserted after ( and before ).
Definition: Format.h:4640
SpacesInParensCustom SpacesInParensOptions
Control of individual spaces in parentheses.
Definition: Format.h:4716
std::vector< std::string > ForEachMacros
A vector of macros that should be interpreted as foreach loops instead of as function calls.
Definition: Format.h:2633
ReferenceAlignmentStyle ReferenceAlignment
Reference alignment style (overrides PointerAlignment for references).
Definition: Format.h:3744
AlignConsecutiveStyle AlignConsecutiveTableGenDefinitionColons
Style of aligning consecutive TableGen definition colons.
Definition: Format.h:469
TrailingCommaStyle InsertTrailingCommas
If set to TCS_Wrapped will insert trailing commas in container literals (arrays and objects) that wra...
Definition: Format.h:2933
unsigned PenaltyBreakTemplateDeclaration
The penalty for breaking after template declaration.
Definition: Format.h:3535
SpaceBeforeParensCustom SpaceBeforeParensOptions
Control of individual space before parentheses.
Definition: Format.h:4468
BreakConstructorInitializersStyle BreakConstructorInitializers
The break constructor initializers style to use.
Definition: Format.h:2256
bool BreakStringLiterals
Allow breaking string literals when formatting.
Definition: Format.h:2323
bool SpaceAfterLogicalNot
If true, a space is inserted after the logical not operator (!).
Definition: Format.h:4181
@ SBPO_Custom
Configure each individual space before parentheses in SpaceBeforeParensOptions.
Definition: Format.h:4337
@ SBPO_NonEmptyParentheses
Put a space before opening parentheses only if the parentheses are not empty i.e.
Definition: Format.h:4322
@ SBPO_ControlStatementsExceptControlMacros
Same as SBPO_ControlStatements except this option doesn't apply to ForEach and If macros.
Definition: Format.h:4311
@ SBPO_ControlStatements
Put a space before opening parentheses only after control statement keywords (for/if/while....
Definition: Format.h:4298
@ SBPO_Always
Always put a space before opening parentheses, except when it's prohibited by the syntax rules (in fu...
Definition: Format.h:4334
@ PCIS_BinPack
Bin-pack constructor initializers.
Definition: Format.h:3458
@ PCIS_NextLine
Same as PCIS_CurrentLine except that if all constructor initializers do not fit on the current line,...
Definition: Format.h:3483
std::vector< std::string > TypeNames
A vector of non-keyword identifiers that should be interpreted as type names.
Definition: Format.h:4858
bool ObjCSpaceAfterProperty
Add a space after @property in Objective-C, i.e.
Definition: Format.h:3436
BraceBreakingStyle BreakBeforeBraces
The brace breaking style to use.
Definition: Format.h:2158
@ BILS_BeforeColon
Break inheritance list before the colon and after the commas.
Definition: Format.h:2352
@ BILS_BeforeComma
Break inheritance list before the colon and commas, and align the commas with the colon.
Definition: Format.h:2361
unsigned PenaltyExcessCharacter
The penalty for each character outside of the column limit.
Definition: Format.h:3539
std::vector< std::string > WhitespaceSensitiveMacros
A vector of macros which are whitespace-sensitive and should not be touched.
Definition: Format.h:4931
bool BinPackParameters
If false, a function declaration's or function definition's parameters will either all be on the same...
Definition: Format.h:1202
@ DAS_DontBreak
Never break inside DAGArg.
Definition: Format.h:4824
unsigned ConstructorInitializerIndentWidth
This option is deprecated.
Definition: Format.h:2419
@ BBNSS_Never
No line break allowed.
Definition: Format.h:683
bool CompactNamespaces
If true, consecutive namespace declarations will be on the same line.
Definition: Format.h:2409
@ RCPS_OwnLine
Always put the requires clause on its own line.
Definition: Format.h:3892
LanguageStandard
Supported language standards for parsing and formatting C++ constructs.
Definition: Format.h:4737
@ LS_Cpp17
Parse and format as C++17.
Definition: Format.h:4746
@ LS_Latest
Parse and format using the latest supported language version.
Definition: Format.h:4751
@ LS_Cpp11
Parse and format as C++11.
Definition: Format.h:4742
@ LS_Auto
Automatic detection based on the input.
Definition: Format.h:4753
@ LS_Cpp03
Parse and format as C++03.
Definition: Format.h:4740
@ LS_Cpp14
Parse and format as C++14.
Definition: Format.h:4744
@ LS_Cpp20
Parse and format as C++20.
Definition: Format.h:4748
@ BWACS_Always
Always wrap braces after a control statement.
Definition: Format.h:1297
@ BWACS_Never
Never wrap braces after a control statement.
Definition: Format.h:1276
RequiresClausePositionStyle RequiresClausePosition
The position of the requires clause.
Definition: Format.h:3952
@ JSQS_Single
Always use single quotes.
Definition: Format.h:3062
@ JSQS_Leave
Leave string quotes as they are.
Definition: Format.h:3056
bool SpaceAfterCStyleCast
If true, a space is inserted after C style casts.
Definition: Format.h:4173
AlignConsecutiveStyle AlignConsecutiveBitFields
Style of aligning consecutive bit fields.
Definition: Format.h:307
int PPIndentWidth
The number of columns to use for indentation of preprocessor statements.
Definition: Format.h:3586
AlignConsecutiveStyle AlignConsecutiveDeclarations
Style of aligning consecutive declarations.
Definition: Format.h:318
IntegerLiteralSeparatorStyle IntegerLiteralSeparator
Format integer literal separators (' for C++ and _ for C#, Java, and JavaScript).
Definition: Format.h:3012
SpaceAroundPointerQualifiersStyle SpaceAroundPointerQualifiers
Defines in which cases to put a space before or after pointer qualifiers.
Definition: Format.h:4222
DefinitionReturnTypeBreakingStyle AlwaysBreakAfterDefinitionReturnType
The function definition return type breaking style to use.
Definition: Format.h:1078
bool SpaceBeforeAssignmentOperators
If false, spaces will be removed before assignment operators.
Definition: Format.h:4231
BreakBeforeInlineASMColonStyle BreakBeforeInlineASMColon
The inline ASM colon style to use.
Definition: Format.h:2211
@ BS_Mozilla
Like Attach, but break before braces on enum, function, and record definitions.
Definition: Format.h:1871
@ BS_Whitesmiths
Like Allman but always indent braces and line up code with braces.
Definition: Format.h:2041
@ BS_Allman
Always break before braces.
Definition: Format.h:1981
@ BS_Stroustrup
Like Attach, but break before function definitions, catch, and else.
Definition: Format.h:1921
@ BS_Linux
Like Attach, but break before braces on function, namespace and class definitions.
Definition: Format.h:1821
@ BS_WebKit
Like Attach, but break before functions.
Definition: Format.h:2151
@ BS_Custom
Configure each individual brace in BraceWrapping.
Definition: Format.h:2153
@ BS_GNU
Always break before braces and add an extra level of indentation to braces of control statements,...
Definition: Format.h:2104
@ BS_Attach
Always attach braces to surrounding context.
Definition: Format.h:1771
@ ABS_Leave
Leave the line breaking after attributes as is.
Definition: Format.h:1615
bool BinPackArguments
If false, a function call's arguments will either be all on the same line or will have one line each.
Definition: Format.h:1187
ShortLambdaStyle AllowShortLambdasOnASingleLine
Dependent on the value, auto lambda []() { return 0; } can be put on a single line.
Definition: Format.h:962
unsigned PenaltyBreakScopeResolution
The penalty for breaking after ::.
Definition: Format.h:3527
unsigned PenaltyReturnTypeOnItsOwnLine
Penalty for putting the return type of a function onto its own line.
Definition: Format.h:3548
@ BFCS_Both
Add one space on each side of the :
Definition: Format.h:1210
PointerAlignmentStyle PointerAlignment
Pointer and reference alignment style.
Definition: Format.h:3571
@ SFS_Inline
Only merge functions defined inside a class.
Definition: Format.h:843
@ SFS_All
Merge all functions fitting on a single line.
Definition: Format.h:851
@ SFS_Empty
Only merge empty functions.
Definition: Format.h:832
@ SFS_None
Never merge functions into a single line.
Definition: Format.h:810
bool BreakFunctionDefinitionParameters
If true, clang-format will always break before function definition parameters.
Definition: Format.h:2270
@ REI_OuterScope
Align requires expression body relative to the indentation level of the outer scope the requires expr...
Definition: Format.h:3965
PackConstructorInitializersStyle PackConstructorInitializers
The pack constructor initializers style to use.
Definition: Format.h:3503
@ BBCDS_Always
Always break before concept, putting it in the line after the template declaration.
Definition: Format.h:2177
bool AllowAllParametersOfDeclarationOnNextLine
This option is deprecated.
Definition: Format.h:670
BracketAlignmentStyle AlignAfterOpenBracket
If true, horizontally aligns arguments after an open bracket.
Definition: Format.h:107
AlignConsecutiveStyle AlignConsecutiveTableGenCondOperatorColons
Style of aligning consecutive TableGen cond operator colons.
Definition: Format.h:459
bool AllowShortCaseExpressionOnASingleLine
Whether to merge a short switch labeled rule into a single line.
Definition: Format.h:757
bool ReflowComments
If true, clang-format will attempt to re-flow comments.
Definition: Format.h:3762
unsigned MaxEmptyLinesToKeep
The maximum number of consecutive empty lines to keep.
Definition: Format.h:3289
bool SpaceBeforeSquareBrackets
If true, spaces will be before [.
Definition: Format.h:4478
BinPackStyle ObjCBinPackProtocolList
Controls bin-packing Objective-C protocol conformance list items into as few lines as possible when t...
Definition: Format.h:3373
ShortCaseStatementsAlignmentStyle AlignConsecutiveShortCaseStatements
Style of aligning consecutive short case labels.
Definition: Format.h:434
EscapedNewlineAlignmentStyle AlignEscapedNewlines
Options for aligning backslashes in escaped newlines.
Definition: Format.h:504
SpacesInLineComment SpacesInLineCommentPrefix
How many spaces are allowed at the start of a line comment.
Definition: Format.h:4611
std::string CommentPragmas
A regular expression that describes comments with special meaning, which should not be split into lin...
Definition: Format.h:2341
bool isJavaScript() const
Definition: Format.h:3177
DAGArgStyle TableGenBreakInsideDAGArg
The styles of the line break inside the DAGArg in TableGen.
Definition: Format.h:4844
JavaScriptQuoteStyle JavaScriptQuotes
The JavaScriptQuoteStyle to use for JavaScript strings.
Definition: Format.h:3073
bool SpacesInContainerLiterals
If true, spaces will be inserted around if/for/switch/while conditions.
Definition: Format.h:4563
SortJavaStaticImportOptions SortJavaStaticImport
When sorting Java imports, by default static imports are placed before non-static imports.
Definition: Format.h:4121
@ SAPQ_Default
Don't ensure spaces around pointer qualifiers and use PointerAlignment instead.
Definition: Format.h:4199
bool SpaceBeforeRangeBasedForLoopColon
If false, spaces will be removed before range-based for loop colon.
Definition: Format.h:4487
bool DisableFormat
Disables formatting completely.
Definition: Format.h:2470
@ ELAAMS_Never
Remove all empty lines after access modifiers.
Definition: Format.h:2490
@ DRTBS_All
Always break after the return type.
Definition: Format.h:976
@ DRTBS_TopLevel
Always break after the return types of top-level functions.
Definition: Format.h:978
@ DRTBS_None
Break after return type automatically.
Definition: Format.h:974
std::vector< std::string > NamespaceMacros
A vector of macros which are used to open namespace blocks.
Definition: Format.h:3340
AttributeBreakingStyle BreakAfterAttributes
Break after a group of C++11 attributes before variable or function (including constructor/destructor...
Definition: Format.h:1645
TrailingCommentsAlignmentStyle AlignTrailingComments
Control of trailing comments.
Definition: Format.h:630
@ AIAS_None
Don't align array initializer columns.
Definition: Format.h:132
LambdaBodyIndentationKind LambdaBodyIndentation
The indentation style of lambda bodies.
Definition: Format.h:3139
QualifierAlignmentStyle QualifierAlignment
Different ways to arrange specifiers and qualifiers (e.g.
Definition: Format.h:3632
bool IndentGotoLabels
Indent goto labels.
Definition: Format.h:2742
BraceWrappingFlags BraceWrapping
Control of individual brace wrapping cases.
Definition: Format.h:1545
@ ENAS_Left
Align escaped newlines as far left as possible.
Definition: Format.h:491
@ ENAS_Right
Align escaped newlines in the right-most column.
Definition: Format.h:499
AlignConsecutiveStyle AlignConsecutiveMacros
Style of aligning consecutive macro definitions.
Definition: Format.h:286
std::vector< std::string > StatementMacros
A vector of macros that should be interpreted as complete statements.
Definition: Format.h:4790
@ SIAS_Never
Remove spaces after < and before >.
Definition: Format.h:4532
@ SUD_LexicographicNumeric
Using declarations are sorted in the order defined as follows: Split the strings by "::" and discard ...
Definition: Format.h:4160
@ SUD_Never
Using declarations are never sorted.
Definition: Format.h:4133
AlignConsecutiveStyle AlignConsecutiveAssignments
Style of aligning consecutive assignments.
Definition: Format.h:296
ShortIfStyle AllowShortIfStatementsOnASingleLine
Dependent on the value, if (a) return; can be put on a single line.
Definition: Format.h:928
@ RPS_Leave
Do not remove parentheses.
Definition: Format.h:3827
@ RPS_ReturnStatement
Also remove parentheses enclosing the expression in a return/co_return statement.
Definition: Format.h:3842
std::vector< std::string > TableGenBreakingDAGArgOperators
Works only when TableGenBreakInsideDAGArg is not DontBreak.
Definition: Format.h:4816
EmptyLineBeforeAccessModifierStyle EmptyLineBeforeAccessModifier
Defines in which cases to put empty line before access modifiers.
Definition: Format.h:2584
bool SpaceBeforeCaseColon
If false, spaces will be removed before case colon.
Definition: Format.h:4241
BreakBeforeNoexceptSpecifierStyle AllowBreakBeforeNoexceptSpecifier
Controls if there could be a line break before a noexcept specifier.
Definition: Format.h:711
bool JavaScriptWrapImports
Whether to wrap JavaScript import/export statements.
Definition: Format.h:3089
bool SkipMacroDefinitionBody
Do not format macro definition body.
Definition: Format.h:4062
unsigned PenaltyBreakAssignment
The penalty for breaking around an assignment operator.
Definition: Format.h:3507
@ PAS_Left
Align pointer to the left.
Definition: Format.h:3556
@ PAS_Right
Align pointer to the right.
Definition: Format.h:3561
unsigned PenaltyBreakString
The penalty for each line break introduced inside a string literal.
Definition: Format.h:3531
RequiresExpressionIndentationKind RequiresExpressionIndentation
The indentation used for requires expression bodies.
Definition: Format.h:3978
bool SpaceAfterTemplateKeyword
If true, a space will be inserted after the 'template' keyword.
Definition: Format.h:4189
unsigned PenaltyIndentedWhitespace
Penalty for each character of whitespace indentation (counted relative to leading non-whitespace colu...
Definition: Format.h:3544
ArrayInitializerAlignmentStyle AlignArrayOfStructures
if not None, when using initialization for an array of structs aligns the fields into columns.
Definition: Format.h:143
@ NI_None
Don't indent in namespaces.
Definition: Format.h:3302
@ NI_All
Indent in all namespaces.
Definition: Format.h:3322
@ NI_Inner
Indent only in inner namespaces (nested in other namespaces).
Definition: Format.h:3312
bool KeepEmptyLinesAtEOF
Keep empty lines (up to MaxEmptyLinesToKeep) at end of file.
Definition: Format.h:3094
ShortBlockStyle AllowShortBlocksOnASingleLine
Dependent on the value, while (true) { continue; } can be put on a single line.
Definition: Format.h:744
std::string MacroBlockEnd
A regular expression matching macros that end a block.
Definition: Format.h:3235
ShortFunctionStyle AllowShortFunctionsOnASingleLine
Dependent on the value, int f() { return 0; } can be put on a single line.
Definition: Format.h:857
bool AllowAllArgumentsOnNextLine
If a function call or braced initializer list doesn't fit on a line, allow putting all arguments onto...
Definition: Format.h:647
bool KeepEmptyLinesAtTheStartOfBlocks
If true, the empty line at the start of blocks is kept.
Definition: Format.h:3105
unsigned PenaltyBreakComment
The penalty for each line break introduced inside a comment.
Definition: Format.h:3515
@ RTBS_TopLevel
Always break after the return types of top-level functions.
Definition: Format.h:1041
@ RTBS_None
This is deprecated. See Automatic below.
Definition: Format.h:985
@ RTBS_AllDefinitions
Always break after the return type of function definitions.
Definition: Format.h:1058
@ RAS_Pointer
Align reference like PointerAlignment.
Definition: Format.h:3723
EmptyLineAfterAccessModifierStyle EmptyLineAfterAccessModifier
Defines when to put an empty line after access modifiers.
Definition: Format.h:2521
bool IndentAccessModifiers
Specify whether access modifiers should have their own indentation level.
Definition: Format.h:2683
bool InsertNewlineAtEOF
Insert a newline at end of file if missing.
Definition: Format.h:2903
SpaceBeforeParensStyle SpaceBeforeParens
Defines in which cases to put a space before opening parentheses.
Definition: Format.h:4342
bool SpaceBeforeCpp11BracedList
If true, a space will be inserted before a C++11 braced list used to initialize an object (after the ...
Definition: Format.h:4253
UseTabStyle UseTab
The way to use tab characters in the resulting file.
Definition: Format.h:4900
@ QAS_Leave
Don't change specifiers/qualifiers to either Left or Right alignment (default).
Definition: Format.h:3596
std::vector< std::string > TypenameMacros
A vector of macros that should be interpreted as type declarations instead of as function calls.
Definition: Format.h:4875
@ OAS_Align
Horizontally align operands of binary and ternary expressions.
Definition: Format.h:527
@ OAS_DontAlign
Do not align operands of binary and ternary expressions.
Definition: Format.h:511
LineEndingStyle LineEnding
Line ending style (\n or \r\n) to use.
Definition: Format.h:3202
bool BreakBeforeTernaryOperators
If true, ternary operators will be placed after line breaks.
Definition: Format.h:2226
unsigned ShortNamespaceLines
The maximal number of unwrapped lines that a short namespace spans.
Definition: Format.h:4058
SortUsingDeclarationsOptions SortUsingDeclarations
Controls if and how clang-format will sort using declarations.
Definition: Format.h:4165
IndentExternBlockStyle IndentExternBlock
IndentExternBlockStyle is the type of indenting of extern blocks.
Definition: Format.h:2782
SeparateDefinitionStyle SeparateDefinitionBlocks
Specifies the use of empty lines to separate definition blocks, including classes,...
Definition: Format.h:4036
tooling::IncludeStyle IncludeStyle
Definition: Format.h:2635
unsigned ColumnLimit
The column limit.
Definition: Format.h:2331
Represents the status of a formatting attempt.
Definition: Format.h:5264
MainIncludeCharDiscriminator MainIncludeChar
When guessing whether a #include is the "main" include, only the include directives that use the spec...
Definition: IncludeStyle.h:168
@ IBS_Preserve
Sort each #include block separately.
Definition: IncludeStyle.h:30
@ IBS_Regroup
Merge multiple #include blocks together and sort as one.
Definition: IncludeStyle.h:48
@ IBS_Merge
Merge multiple #include blocks together and sort as one.
Definition: IncludeStyle.h:38
std::string IncludeIsMainRegex
Specify a regular expression of suffixes that are allowed in the file-to-main-include mapping.
Definition: IncludeStyle.h:132
std::string IncludeIsMainSourceRegex
Specify a regular expression for files being formatted that are allowed to be considered "main" in th...
Definition: IncludeStyle.h:153
@ MICD_Quote
Main include uses quotes: #include "foo.hpp" (the default).
Definition: IncludeStyle.h:158
IncludeBlocksStyle IncludeBlocks
Dependent on the value, multiple #include blocks can be sorted as one and divided based on category.
Definition: IncludeStyle.h:54
std::vector< IncludeCategory > IncludeCategories
Regular expressions denoting the different #include categories used for ordering #includes.
Definition: IncludeStyle.h:118
static FormatStyle & element(IO &IO, std::vector< FormatStyle > &Seq, size_t Index)
Definition: Format.cpp:1208
static size_t size(IO &IO, std::vector< FormatStyle > &Seq)
Definition: Format.cpp:1205
static void mapping(IO &IO, FormatStyle &Style)
Definition: Format.cpp:799
static void enumInput(IO &IO, FormatStyle::AlignConsecutiveStyle &Value)
Definition: Format.cpp:46
static void mapping(IO &IO, FormatStyle::AlignConsecutiveStyle &Value)
Definition: Format.cpp:86
static void mapping(IO &IO, FormatStyle::BraceWrappingFlags &Wrapping)
Definition: Format.cpp:171
static void mapping(IO &IO, FormatStyle::IntegerLiteralSeparatorStyle &Base)
Definition: Format.cpp:353
static void mapping(IO &IO, FormatStyle::RawStringFormat &Format)
Definition: Format.cpp:490
static void mapping(IO &IO, FormatStyle::ShortCaseStatementsAlignmentStyle &Value)
Definition: Format.cpp:98
static void mapping(IO &IO, FormatStyle::SpaceBeforeParensCustom &Spacing)
Definition: Format.cpp:657
static void mapping(IO &IO, FormatStyle::SpacesInLineComment &Space)
Definition: Format.cpp:709
static void mapping(IO &IO, FormatStyle::SpacesInParensCustom &Spaces)
Definition: Format.cpp:722
static void mapping(IO &IO, FormatStyle::TrailingCommentsAlignmentStyle &Value)
Definition: Format.cpp:778
static void enumInput(IO &IO, FormatStyle::TrailingCommentsAlignmentStyle &Value)
Definition: Format.cpp:755
static void enumeration(IO &IO, FormatStyle::ArrayInitializerAlignmentStyle &Value)
Definition: Format.cpp:119
static void enumeration(IO &IO, FormatStyle::AttributeBreakingStyle &Value)
Definition: Format.cpp:110
static void enumeration(IO &IO, FormatStyle::BinPackStyle &Value)
Definition: Format.cpp:138
static void enumeration(IO &IO, FormatStyle::BinaryOperatorStyle &Value)
Definition: Format.cpp:128
static void enumeration(IO &IO, FormatStyle::BitFieldColonSpacingStyle &Value)
Definition: Format.cpp:147
static void enumeration(IO &IO, FormatStyle::BraceBreakingStyle &Value)
Definition: Format.cpp:157
static void enumeration(IO &IO, FormatStyle::BraceWrappingAfterControlStatementStyle &Value)
Definition: Format.cpp:210
static void enumeration(IO &IO, FormatStyle::BracketAlignmentStyle &Value)
Definition: Format.cpp:194
static void enumeration(IO &IO, FormatStyle::BreakBeforeConceptDeclarationsStyle &Value)
Definition: Format.cpp:226
static void enumeration(IO &IO, FormatStyle::BreakBeforeInlineASMColonStyle &Value)
Definition: Format.cpp:239
static void enumeration(IO &IO, FormatStyle::BreakBeforeNoexceptSpecifierStyle &Value)
Definition: Format.cpp:38
static void enumeration(IO &IO, FormatStyle::BreakConstructorInitializersStyle &Value)
Definition: Format.cpp:250
static void enumeration(IO &IO, FormatStyle::BreakInheritanceListStyle &Value)
Definition: Format.cpp:259
static void enumeration(IO &IO, FormatStyle::BreakTemplateDeclarationsStyle &Value)
Definition: Format.cpp:270
static void enumeration(IO &IO, FormatStyle::DAGArgStyle &Value)
Definition: Format.cpp:284
static void enumeration(IO &IO, FormatStyle::DefinitionReturnTypeBreakingStyle &Value)
Definition: Format.cpp:294
static void enumeration(IO &IO, FormatStyle::EmptyLineAfterAccessModifierStyle &Value)
Definition: Format.cpp:322
static void enumeration(IO &IO, FormatStyle::EmptyLineBeforeAccessModifierStyle &Value)
Definition: Format.cpp:333
static void enumeration(IO &IO, FormatStyle::EscapedNewlineAlignmentStyle &Value)
Definition: Format.cpp:307
static void enumeration(IO &IO, FormatStyle::IndentExternBlockStyle &Value)
Definition: Format.cpp:343
static void enumeration(IO &IO, FormatStyle::JavaScriptQuoteStyle &Value)
Definition: Format.cpp:364
static void enumeration(IO &IO, FormatStyle::LambdaBodyIndentationKind &Value)
Definition: Format.cpp:407
static void enumeration(IO &IO, FormatStyle::LanguageKind &Value)
Definition: Format.cpp:372
static void enumeration(IO &IO, FormatStyle::LanguageStandard &Value)
Definition: Format.cpp:387
static void enumeration(IO &IO, FormatStyle::LineEndingStyle &Value)
Definition: Format.cpp:415
static void enumeration(IO &IO, FormatStyle::NamespaceIndentationKind &Value)
Definition: Format.cpp:425
static void enumeration(IO &IO, FormatStyle::OperandAlignmentStyle &Value)
Definition: Format.cpp:434
static void enumeration(IO &IO, FormatStyle::PPDirectiveIndentStyle &Value)
Definition: Format.cpp:472
static void enumeration(IO &IO, FormatStyle::PackConstructorInitializersStyle &Value)
Definition: Format.cpp:449
static void enumeration(IO &IO, FormatStyle::PointerAlignmentStyle &Value)
Definition: Format.cpp:459
static void enumeration(IO &IO, FormatStyle::QualifierAlignmentStyle &Value)
Definition: Format.cpp:481
static void enumeration(IO &IO, FormatStyle::ReferenceAlignmentStyle &Value)
Definition: Format.cpp:501
static void enumeration(IO &IO, FormatStyle::RemoveParenthesesStyle &Value)
Definition: Format.cpp:511
static void enumeration(IO &IO, FormatStyle::RequiresClausePositionStyle &Value)
Definition: Format.cpp:521
static void enumeration(IO &IO, FormatStyle::RequiresExpressionIndentationKind &Value)
Definition: Format.cpp:533
static void enumeration(IO &IO, FormatStyle::ReturnTypeBreakingStyle &Value)
Definition: Format.cpp:541
static void enumeration(IO &IO, FormatStyle::SeparateDefinitionStyle &Value)
Definition: Format.cpp:555
static void enumeration(IO &IO, FormatStyle::ShortBlockStyle &Value)
Definition: Format.cpp:563
static void enumeration(IO &IO, FormatStyle::ShortFunctionStyle &Value)
Definition: Format.cpp:573
static void enumeration(IO &IO, FormatStyle::ShortIfStyle &Value)
Definition: Format.cpp:585
static void enumeration(IO &IO, FormatStyle::ShortLambdaStyle &Value)
Definition: Format.cpp:599
static void enumeration(IO &IO, FormatStyle::SortIncludesOptions &Value)
Definition: Format.cpp:610
static void enumeration(IO &IO, FormatStyle::SortJavaStaticImportOptions &Value)
Definition: Format.cpp:623
static void enumeration(IO &IO, FormatStyle::SortUsingDeclarationsOptions &Value)
Definition: Format.cpp:632
static void enumeration(IO &IO, FormatStyle::SpaceAroundPointerQualifiersStyle &Value)
Definition: Format.cpp:648
static void enumeration(IO &IO, FormatStyle::SpaceBeforeParensStyle &Value)
Definition: Format.cpp:677
static void enumeration(IO &IO, FormatStyle::SpacesInAnglesStyle &Value)
Definition: Format.cpp:697
static void enumeration(IO &IO, FormatStyle::SpacesInParensStyle &Value)
Definition: Format.cpp:731
static void enumeration(IO &IO, FormatStyle::TrailingCommaStyle &Value)
Definition: Format.cpp:738
static void enumeration(IO &IO, FormatStyle::TrailingCommentsAlignmentKinds &Value)
Definition: Format.cpp:746
static void enumeration(IO &IO, FormatStyle::UseTabStyle &Value)
Definition: Format.cpp:786