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