clang  10.0.0svn
Format.cpp
Go to the documentation of this file.
1 //===--- Format.cpp - Format C++ code -------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 ///
9 /// \file
10 /// This file implements functions declared in Format.h. This will be
11 /// split into separate files as we go.
12 ///
13 //===----------------------------------------------------------------------===//
14 
15 #include "clang/Format/Format.h"
16 #include "AffectedRangeManager.h"
17 #include "ContinuationIndenter.h"
18 #include "FormatInternal.h"
19 #include "FormatTokenLexer.h"
21 #include "SortJavaScriptImports.h"
22 #include "TokenAnalyzer.h"
23 #include "TokenAnnotator.h"
24 #include "UnwrappedLineFormatter.h"
25 #include "UnwrappedLineParser.h"
27 #include "WhitespaceManager.h"
28 #include "clang/Basic/Diagnostic.h"
31 #include "clang/Lex/Lexer.h"
33 #include "llvm/ADT/STLExtras.h"
34 #include "llvm/ADT/StringRef.h"
35 #include "llvm/Support/Allocator.h"
36 #include "llvm/Support/Debug.h"
37 #include "llvm/Support/Path.h"
38 #include "llvm/Support/Regex.h"
39 #include "llvm/Support/VirtualFileSystem.h"
40 #include "llvm/Support/YAMLTraits.h"
41 #include <algorithm>
42 #include <memory>
43 #include <mutex>
44 #include <string>
45 #include <unordered_map>
46 
47 #define DEBUG_TYPE "format-formatter"
48 
50 
51 LLVM_YAML_IS_SEQUENCE_VECTOR(clang::format::FormatStyle::RawStringFormat)
52 
53 namespace llvm {
54 namespace yaml {
55 template <> struct ScalarEnumerationTraits<FormatStyle::LanguageKind> {
56  static void enumeration(IO &IO, FormatStyle::LanguageKind &Value) {
57  IO.enumCase(Value, "Cpp", FormatStyle::LK_Cpp);
58  IO.enumCase(Value, "Java", FormatStyle::LK_Java);
59  IO.enumCase(Value, "JavaScript", FormatStyle::LK_JavaScript);
60  IO.enumCase(Value, "ObjC", FormatStyle::LK_ObjC);
61  IO.enumCase(Value, "Proto", FormatStyle::LK_Proto);
62  IO.enumCase(Value, "TableGen", FormatStyle::LK_TableGen);
63  IO.enumCase(Value, "TextProto", FormatStyle::LK_TextProto);
64  IO.enumCase(Value, "CSharp", FormatStyle::LK_CSharp);
65  }
66 };
67 
68 template <> struct ScalarEnumerationTraits<FormatStyle::LanguageStandard> {
69  static void enumeration(IO &IO, FormatStyle::LanguageStandard &Value) {
70  IO.enumCase(Value, "Cpp03", FormatStyle::LS_Cpp03);
71  IO.enumCase(Value, "C++03", FormatStyle::LS_Cpp03);
72  IO.enumCase(Value, "Cpp11", FormatStyle::LS_Cpp11);
73  IO.enumCase(Value, "C++11", FormatStyle::LS_Cpp11);
74  IO.enumCase(Value, "Auto", FormatStyle::LS_Auto);
75  }
76 };
77 
78 template <> struct ScalarEnumerationTraits<FormatStyle::UseTabStyle> {
79  static void enumeration(IO &IO, FormatStyle::UseTabStyle &Value) {
80  IO.enumCase(Value, "Never", FormatStyle::UT_Never);
81  IO.enumCase(Value, "false", FormatStyle::UT_Never);
82  IO.enumCase(Value, "Always", FormatStyle::UT_Always);
83  IO.enumCase(Value, "true", FormatStyle::UT_Always);
84  IO.enumCase(Value, "ForIndentation", FormatStyle::UT_ForIndentation);
85  IO.enumCase(Value, "ForContinuationAndIndentation",
86  FormatStyle::UT_ForContinuationAndIndentation);
87  }
88 };
89 
90 template <> struct ScalarEnumerationTraits<FormatStyle::JavaScriptQuoteStyle> {
91  static void enumeration(IO &IO, FormatStyle::JavaScriptQuoteStyle &Value) {
92  IO.enumCase(Value, "Leave", FormatStyle::JSQS_Leave);
93  IO.enumCase(Value, "Single", FormatStyle::JSQS_Single);
94  IO.enumCase(Value, "Double", FormatStyle::JSQS_Double);
95  }
96 };
97 
98 template <> struct ScalarEnumerationTraits<FormatStyle::ShortBlockStyle> {
99  static void enumeration(IO &IO, FormatStyle::ShortBlockStyle &Value) {
100  IO.enumCase(Value, "Never", FormatStyle::SBS_Never);
101  IO.enumCase(Value, "false", FormatStyle::SBS_Never);
102  IO.enumCase(Value, "Always", FormatStyle::SBS_Always);
103  IO.enumCase(Value, "true", FormatStyle::SBS_Always);
104  IO.enumCase(Value, "Empty", FormatStyle::SBS_Empty);
105  }
106 };
107 
108 template <> struct ScalarEnumerationTraits<FormatStyle::ShortFunctionStyle> {
109  static void enumeration(IO &IO, FormatStyle::ShortFunctionStyle &Value) {
110  IO.enumCase(Value, "None", FormatStyle::SFS_None);
111  IO.enumCase(Value, "false", FormatStyle::SFS_None);
112  IO.enumCase(Value, "All", FormatStyle::SFS_All);
113  IO.enumCase(Value, "true", FormatStyle::SFS_All);
114  IO.enumCase(Value, "Inline", FormatStyle::SFS_Inline);
115  IO.enumCase(Value, "InlineOnly", FormatStyle::SFS_InlineOnly);
116  IO.enumCase(Value, "Empty", FormatStyle::SFS_Empty);
117  }
118 };
119 
120 template <> struct ScalarEnumerationTraits<FormatStyle::ShortIfStyle> {
121  static void enumeration(IO &IO, FormatStyle::ShortIfStyle &Value) {
122  IO.enumCase(Value, "Never", FormatStyle::SIS_Never);
123  IO.enumCase(Value, "Always", FormatStyle::SIS_Always);
124  IO.enumCase(Value, "WithoutElse", FormatStyle::SIS_WithoutElse);
125 
126  // For backward compatibility.
127  IO.enumCase(Value, "false", FormatStyle::SIS_Never);
128  IO.enumCase(Value, "true", FormatStyle::SIS_WithoutElse);
129  }
130 };
131 
132 template <> struct ScalarEnumerationTraits<FormatStyle::ShortLambdaStyle> {
133  static void enumeration(IO &IO, FormatStyle::ShortLambdaStyle &Value) {
134  IO.enumCase(Value, "None", FormatStyle::SLS_None);
135  IO.enumCase(Value, "false", FormatStyle::SLS_None);
136  IO.enumCase(Value, "Empty", FormatStyle::SLS_Empty);
137  IO.enumCase(Value, "Inline", FormatStyle::SLS_Inline);
138  IO.enumCase(Value, "All", FormatStyle::SLS_All);
139  IO.enumCase(Value, "true", FormatStyle::SLS_All);
140  }
141 };
142 
143 template <> struct ScalarEnumerationTraits<FormatStyle::BinPackStyle> {
144  static void enumeration(IO &IO, FormatStyle::BinPackStyle &Value) {
145  IO.enumCase(Value, "Auto", FormatStyle::BPS_Auto);
146  IO.enumCase(Value, "Always", FormatStyle::BPS_Always);
147  IO.enumCase(Value, "Never", FormatStyle::BPS_Never);
148  }
149 };
150 
151 template <> struct ScalarEnumerationTraits<FormatStyle::BinaryOperatorStyle> {
152  static void enumeration(IO &IO, FormatStyle::BinaryOperatorStyle &Value) {
153  IO.enumCase(Value, "All", FormatStyle::BOS_All);
154  IO.enumCase(Value, "true", FormatStyle::BOS_All);
155  IO.enumCase(Value, "None", FormatStyle::BOS_None);
156  IO.enumCase(Value, "false", FormatStyle::BOS_None);
157  IO.enumCase(Value, "NonAssignment", FormatStyle::BOS_NonAssignment);
158  }
159 };
160 
161 template <> struct ScalarEnumerationTraits<FormatStyle::BraceBreakingStyle> {
162  static void enumeration(IO &IO, FormatStyle::BraceBreakingStyle &Value) {
163  IO.enumCase(Value, "Attach", FormatStyle::BS_Attach);
164  IO.enumCase(Value, "Linux", FormatStyle::BS_Linux);
165  IO.enumCase(Value, "Mozilla", FormatStyle::BS_Mozilla);
166  IO.enumCase(Value, "Stroustrup", FormatStyle::BS_Stroustrup);
167  IO.enumCase(Value, "Allman", FormatStyle::BS_Allman);
168  IO.enumCase(Value, "GNU", FormatStyle::BS_GNU);
169  IO.enumCase(Value, "WebKit", FormatStyle::BS_WebKit);
170  IO.enumCase(Value, "Custom", FormatStyle::BS_Custom);
171  }
172 };
173 
174 template <>
175 struct ScalarEnumerationTraits<FormatStyle::BreakConstructorInitializersStyle> {
176  static void
177  enumeration(IO &IO, FormatStyle::BreakConstructorInitializersStyle &Value) {
178  IO.enumCase(Value, "BeforeColon", FormatStyle::BCIS_BeforeColon);
179  IO.enumCase(Value, "BeforeComma", FormatStyle::BCIS_BeforeComma);
180  IO.enumCase(Value, "AfterColon", FormatStyle::BCIS_AfterColon);
181  }
182 };
183 
184 template <>
185 struct ScalarEnumerationTraits<FormatStyle::BreakInheritanceListStyle> {
186  static void enumeration(IO &IO,
187  FormatStyle::BreakInheritanceListStyle &Value) {
188  IO.enumCase(Value, "BeforeColon", FormatStyle::BILS_BeforeColon);
189  IO.enumCase(Value, "BeforeComma", FormatStyle::BILS_BeforeComma);
190  IO.enumCase(Value, "AfterColon", FormatStyle::BILS_AfterColon);
191  }
192 };
193 
194 template <>
195 struct ScalarEnumerationTraits<FormatStyle::PPDirectiveIndentStyle> {
196  static void enumeration(IO &IO, FormatStyle::PPDirectiveIndentStyle &Value) {
197  IO.enumCase(Value, "None", FormatStyle::PPDIS_None);
198  IO.enumCase(Value, "AfterHash", FormatStyle::PPDIS_AfterHash);
199  IO.enumCase(Value, "BeforeHash", FormatStyle::PPDIS_BeforeHash);
200  }
201 };
202 
203 template <>
204 struct ScalarEnumerationTraits<FormatStyle::ReturnTypeBreakingStyle> {
205  static void enumeration(IO &IO, FormatStyle::ReturnTypeBreakingStyle &Value) {
206  IO.enumCase(Value, "None", FormatStyle::RTBS_None);
207  IO.enumCase(Value, "All", FormatStyle::RTBS_All);
208  IO.enumCase(Value, "TopLevel", FormatStyle::RTBS_TopLevel);
209  IO.enumCase(Value, "TopLevelDefinitions",
210  FormatStyle::RTBS_TopLevelDefinitions);
211  IO.enumCase(Value, "AllDefinitions", FormatStyle::RTBS_AllDefinitions);
212  }
213 };
214 
215 template <>
216 struct ScalarEnumerationTraits<FormatStyle::BreakTemplateDeclarationsStyle> {
217  static void enumeration(IO &IO,
218  FormatStyle::BreakTemplateDeclarationsStyle &Value) {
219  IO.enumCase(Value, "No", FormatStyle::BTDS_No);
220  IO.enumCase(Value, "MultiLine", FormatStyle::BTDS_MultiLine);
221  IO.enumCase(Value, "Yes", FormatStyle::BTDS_Yes);
222 
223  // For backward compatibility.
224  IO.enumCase(Value, "false", FormatStyle::BTDS_MultiLine);
225  IO.enumCase(Value, "true", FormatStyle::BTDS_Yes);
226  }
227 };
228 
229 template <>
230 struct ScalarEnumerationTraits<FormatStyle::DefinitionReturnTypeBreakingStyle> {
231  static void
232  enumeration(IO &IO, FormatStyle::DefinitionReturnTypeBreakingStyle &Value) {
233  IO.enumCase(Value, "None", FormatStyle::DRTBS_None);
234  IO.enumCase(Value, "All", FormatStyle::DRTBS_All);
235  IO.enumCase(Value, "TopLevel", FormatStyle::DRTBS_TopLevel);
236 
237  // For backward compatibility.
238  IO.enumCase(Value, "false", FormatStyle::DRTBS_None);
239  IO.enumCase(Value, "true", FormatStyle::DRTBS_All);
240  }
241 };
242 
243 template <>
244 struct ScalarEnumerationTraits<FormatStyle::NamespaceIndentationKind> {
245  static void enumeration(IO &IO,
246  FormatStyle::NamespaceIndentationKind &Value) {
247  IO.enumCase(Value, "None", FormatStyle::NI_None);
248  IO.enumCase(Value, "Inner", FormatStyle::NI_Inner);
249  IO.enumCase(Value, "All", FormatStyle::NI_All);
250  }
251 };
252 
253 template <> struct ScalarEnumerationTraits<FormatStyle::BracketAlignmentStyle> {
254  static void enumeration(IO &IO, FormatStyle::BracketAlignmentStyle &Value) {
255  IO.enumCase(Value, "Align", FormatStyle::BAS_Align);
256  IO.enumCase(Value, "DontAlign", FormatStyle::BAS_DontAlign);
257  IO.enumCase(Value, "AlwaysBreak", FormatStyle::BAS_AlwaysBreak);
258 
259  // For backward compatibility.
260  IO.enumCase(Value, "true", FormatStyle::BAS_Align);
261  IO.enumCase(Value, "false", FormatStyle::BAS_DontAlign);
262  }
263 };
264 
265 template <>
266 struct ScalarEnumerationTraits<FormatStyle::EscapedNewlineAlignmentStyle> {
267  static void enumeration(IO &IO,
268  FormatStyle::EscapedNewlineAlignmentStyle &Value) {
269  IO.enumCase(Value, "DontAlign", FormatStyle::ENAS_DontAlign);
270  IO.enumCase(Value, "Left", FormatStyle::ENAS_Left);
271  IO.enumCase(Value, "Right", FormatStyle::ENAS_Right);
272 
273  // For backward compatibility.
274  IO.enumCase(Value, "true", FormatStyle::ENAS_Left);
275  IO.enumCase(Value, "false", FormatStyle::ENAS_Right);
276  }
277 };
278 
279 template <> struct ScalarEnumerationTraits<FormatStyle::PointerAlignmentStyle> {
280  static void enumeration(IO &IO, FormatStyle::PointerAlignmentStyle &Value) {
281  IO.enumCase(Value, "Middle", FormatStyle::PAS_Middle);
282  IO.enumCase(Value, "Left", FormatStyle::PAS_Left);
283  IO.enumCase(Value, "Right", FormatStyle::PAS_Right);
284 
285  // For backward compatibility.
286  IO.enumCase(Value, "true", FormatStyle::PAS_Left);
287  IO.enumCase(Value, "false", FormatStyle::PAS_Right);
288  }
289 };
290 
291 template <>
292 struct ScalarEnumerationTraits<FormatStyle::SpaceBeforeParensOptions> {
293  static void enumeration(IO &IO,
294  FormatStyle::SpaceBeforeParensOptions &Value) {
295  IO.enumCase(Value, "Never", FormatStyle::SBPO_Never);
296  IO.enumCase(Value, "ControlStatements",
297  FormatStyle::SBPO_ControlStatements);
298  IO.enumCase(Value, "NonEmptyParentheses",
299  FormatStyle::SBPO_NonEmptyParentheses);
300  IO.enumCase(Value, "Always", FormatStyle::SBPO_Always);
301 
302  // For backward compatibility.
303  IO.enumCase(Value, "false", FormatStyle::SBPO_Never);
304  IO.enumCase(Value, "true", FormatStyle::SBPO_ControlStatements);
305  }
306 };
307 
308 template <> struct MappingTraits<FormatStyle> {
309  static void mapping(IO &IO, FormatStyle &Style) {
310  // When reading, read the language first, we need it for getPredefinedStyle.
311  IO.mapOptional("Language", Style.Language);
312 
313  if (IO.outputting()) {
314  StringRef StylesArray[] = {"LLVM", "Google", "Chromium", "Mozilla",
315  "WebKit", "GNU", "Microsoft"};
316  ArrayRef<StringRef> Styles(StylesArray);
317  for (size_t i = 0, e = Styles.size(); i < e; ++i) {
318  StringRef StyleName(Styles[i]);
319  FormatStyle PredefinedStyle;
320  if (getPredefinedStyle(StyleName, Style.Language, &PredefinedStyle) &&
321  Style == PredefinedStyle) {
322  IO.mapOptional("# BasedOnStyle", StyleName);
323  break;
324  }
325  }
326  } else {
327  StringRef BasedOnStyle;
328  IO.mapOptional("BasedOnStyle", BasedOnStyle);
329  if (!BasedOnStyle.empty()) {
330  FormatStyle::LanguageKind OldLanguage = Style.Language;
331  FormatStyle::LanguageKind Language =
332  ((FormatStyle *)IO.getContext())->Language;
333  if (!getPredefinedStyle(BasedOnStyle, Language, &Style)) {
334  IO.setError(Twine("Unknown value for BasedOnStyle: ", BasedOnStyle));
335  return;
336  }
337  Style.Language = OldLanguage;
338  }
339  }
340 
341  // For backward compatibility.
342  if (!IO.outputting()) {
343  IO.mapOptional("AlignEscapedNewlinesLeft", Style.AlignEscapedNewlines);
344  IO.mapOptional("DerivePointerBinding", Style.DerivePointerAlignment);
345  IO.mapOptional("IndentFunctionDeclarationAfterType",
346  Style.IndentWrappedFunctionNames);
347  IO.mapOptional("PointerBindsToType", Style.PointerAlignment);
348  IO.mapOptional("SpaceAfterControlStatementKeyword",
349  Style.SpaceBeforeParens);
350  }
351 
352  IO.mapOptional("AccessModifierOffset", Style.AccessModifierOffset);
353  IO.mapOptional("AlignAfterOpenBracket", Style.AlignAfterOpenBracket);
354  IO.mapOptional("AlignConsecutiveMacros", Style.AlignConsecutiveMacros);
355  IO.mapOptional("AlignConsecutiveAssignments",
357  IO.mapOptional("AlignConsecutiveDeclarations",
359  IO.mapOptional("AlignEscapedNewlines", Style.AlignEscapedNewlines);
360  IO.mapOptional("AlignOperands", Style.AlignOperands);
361  IO.mapOptional("AlignTrailingComments", Style.AlignTrailingComments);
362  IO.mapOptional("AllowAllArgumentsOnNextLine",
364  IO.mapOptional("AllowAllConstructorInitializersOnNextLine",
365  Style.AllowAllConstructorInitializersOnNextLine);
366  IO.mapOptional("AllowAllParametersOfDeclarationOnNextLine",
367  Style.AllowAllParametersOfDeclarationOnNextLine);
368  IO.mapOptional("AllowShortBlocksOnASingleLine",
369  Style.AllowShortBlocksOnASingleLine);
370  IO.mapOptional("AllowShortCaseLabelsOnASingleLine",
371  Style.AllowShortCaseLabelsOnASingleLine);
372  IO.mapOptional("AllowShortFunctionsOnASingleLine",
373  Style.AllowShortFunctionsOnASingleLine);
374  IO.mapOptional("AllowShortLambdasOnASingleLine",
375  Style.AllowShortLambdasOnASingleLine);
376  IO.mapOptional("AllowShortIfStatementsOnASingleLine",
377  Style.AllowShortIfStatementsOnASingleLine);
378  IO.mapOptional("AllowShortLoopsOnASingleLine",
379  Style.AllowShortLoopsOnASingleLine);
380  IO.mapOptional("AlwaysBreakAfterDefinitionReturnType",
381  Style.AlwaysBreakAfterDefinitionReturnType);
382  IO.mapOptional("AlwaysBreakAfterReturnType",
383  Style.AlwaysBreakAfterReturnType);
384 
385  // If AlwaysBreakAfterDefinitionReturnType was specified but
386  // AlwaysBreakAfterReturnType was not, initialize the latter from the
387  // former for backwards compatibility.
388  if (Style.AlwaysBreakAfterDefinitionReturnType != FormatStyle::DRTBS_None &&
389  Style.AlwaysBreakAfterReturnType == FormatStyle::RTBS_None) {
390  if (Style.AlwaysBreakAfterDefinitionReturnType == FormatStyle::DRTBS_All)
391  Style.AlwaysBreakAfterReturnType = FormatStyle::RTBS_AllDefinitions;
392  else if (Style.AlwaysBreakAfterDefinitionReturnType ==
393  FormatStyle::DRTBS_TopLevel)
394  Style.AlwaysBreakAfterReturnType =
395  FormatStyle::RTBS_TopLevelDefinitions;
396  }
397 
398  IO.mapOptional("AlwaysBreakBeforeMultilineStrings",
399  Style.AlwaysBreakBeforeMultilineStrings);
400  IO.mapOptional("AlwaysBreakTemplateDeclarations",
401  Style.AlwaysBreakTemplateDeclarations);
402  IO.mapOptional("BinPackArguments", Style.BinPackArguments);
403  IO.mapOptional("BinPackParameters", Style.BinPackParameters);
404  IO.mapOptional("BraceWrapping", Style.BraceWrapping);
405  IO.mapOptional("BreakBeforeBinaryOperators",
406  Style.BreakBeforeBinaryOperators);
407  IO.mapOptional("BreakBeforeBraces", Style.BreakBeforeBraces);
408 
409  bool BreakBeforeInheritanceComma = false;
410  IO.mapOptional("BreakBeforeInheritanceComma", BreakBeforeInheritanceComma);
411  IO.mapOptional("BreakInheritanceList", Style.BreakInheritanceList);
412  // If BreakBeforeInheritanceComma was specified but
413  // BreakInheritance was not, initialize the latter from the
414  // former for backwards compatibility.
415  if (BreakBeforeInheritanceComma &&
416  Style.BreakInheritanceList == FormatStyle::BILS_BeforeColon)
417  Style.BreakInheritanceList = FormatStyle::BILS_BeforeComma;
418 
419  IO.mapOptional("BreakBeforeTernaryOperators",
420  Style.BreakBeforeTernaryOperators);
421 
422  bool BreakConstructorInitializersBeforeComma = false;
423  IO.mapOptional("BreakConstructorInitializersBeforeComma",
424  BreakConstructorInitializersBeforeComma);
425  IO.mapOptional("BreakConstructorInitializers",
426  Style.BreakConstructorInitializers);
427  // If BreakConstructorInitializersBeforeComma was specified but
428  // BreakConstructorInitializers was not, initialize the latter from the
429  // former for backwards compatibility.
430  if (BreakConstructorInitializersBeforeComma &&
431  Style.BreakConstructorInitializers == FormatStyle::BCIS_BeforeColon)
432  Style.BreakConstructorInitializers = FormatStyle::BCIS_BeforeComma;
433 
434  IO.mapOptional("BreakAfterJavaFieldAnnotations",
435  Style.BreakAfterJavaFieldAnnotations);
436  IO.mapOptional("BreakStringLiterals", Style.BreakStringLiterals);
437  IO.mapOptional("ColumnLimit", Style.ColumnLimit);
438  IO.mapOptional("CommentPragmas", Style.CommentPragmas);
439  IO.mapOptional("CompactNamespaces", Style.CompactNamespaces);
440  IO.mapOptional("ConstructorInitializerAllOnOneLineOrOnePerLine",
441  Style.ConstructorInitializerAllOnOneLineOrOnePerLine);
442  IO.mapOptional("ConstructorInitializerIndentWidth",
443  Style.ConstructorInitializerIndentWidth);
444  IO.mapOptional("ContinuationIndentWidth", Style.ContinuationIndentWidth);
445  IO.mapOptional("Cpp11BracedListStyle", Style.Cpp11BracedListStyle);
446  IO.mapOptional("DerivePointerAlignment", Style.DerivePointerAlignment);
447  IO.mapOptional("DisableFormat", Style.DisableFormat);
448  IO.mapOptional("ExperimentalAutoDetectBinPacking",
449  Style.ExperimentalAutoDetectBinPacking);
450  IO.mapOptional("FixNamespaceComments", Style.FixNamespaceComments);
451  IO.mapOptional("ForEachMacros", Style.ForEachMacros);
452  IO.mapOptional("IncludeBlocks", Style.IncludeStyle.IncludeBlocks);
453  IO.mapOptional("IncludeCategories", Style.IncludeStyle.IncludeCategories);
454  IO.mapOptional("IncludeIsMainRegex", Style.IncludeStyle.IncludeIsMainRegex);
455  IO.mapOptional("IndentCaseLabels", Style.IndentCaseLabels);
456  IO.mapOptional("IndentGotoLabels", Style.IndentGotoLabels);
457  IO.mapOptional("IndentPPDirectives", Style.IndentPPDirectives);
458  IO.mapOptional("IndentWidth", Style.IndentWidth);
459  IO.mapOptional("IndentWrappedFunctionNames",
460  Style.IndentWrappedFunctionNames);
461  IO.mapOptional("JavaImportGroups", Style.JavaImportGroups);
462  IO.mapOptional("JavaScriptQuotes", Style.JavaScriptQuotes);
463  IO.mapOptional("JavaScriptWrapImports", Style.JavaScriptWrapImports);
464  IO.mapOptional("KeepEmptyLinesAtTheStartOfBlocks",
465  Style.KeepEmptyLinesAtTheStartOfBlocks);
466  IO.mapOptional("MacroBlockBegin", Style.MacroBlockBegin);
467  IO.mapOptional("MacroBlockEnd", Style.MacroBlockEnd);
468  IO.mapOptional("MaxEmptyLinesToKeep", Style.MaxEmptyLinesToKeep);
469  IO.mapOptional("NamespaceIndentation", Style.NamespaceIndentation);
470  IO.mapOptional("NamespaceMacros", Style.NamespaceMacros);
471  IO.mapOptional("ObjCBinPackProtocolList", Style.ObjCBinPackProtocolList);
472  IO.mapOptional("ObjCBlockIndentWidth", Style.ObjCBlockIndentWidth);
473  IO.mapOptional("ObjCSpaceAfterProperty", Style.ObjCSpaceAfterProperty);
474  IO.mapOptional("ObjCSpaceBeforeProtocolList",
475  Style.ObjCSpaceBeforeProtocolList);
476  IO.mapOptional("PenaltyBreakAssignment", Style.PenaltyBreakAssignment);
477  IO.mapOptional("PenaltyBreakBeforeFirstCallParameter",
478  Style.PenaltyBreakBeforeFirstCallParameter);
479  IO.mapOptional("PenaltyBreakComment", Style.PenaltyBreakComment);
480  IO.mapOptional("PenaltyBreakFirstLessLess",
481  Style.PenaltyBreakFirstLessLess);
482  IO.mapOptional("PenaltyBreakString", Style.PenaltyBreakString);
483  IO.mapOptional("PenaltyBreakTemplateDeclaration",
484  Style.PenaltyBreakTemplateDeclaration);
485  IO.mapOptional("PenaltyExcessCharacter", Style.PenaltyExcessCharacter);
486  IO.mapOptional("PenaltyReturnTypeOnItsOwnLine",
487  Style.PenaltyReturnTypeOnItsOwnLine);
488  IO.mapOptional("PointerAlignment", Style.PointerAlignment);
489  IO.mapOptional("RawStringFormats", Style.RawStringFormats);
490  IO.mapOptional("ReflowComments", Style.ReflowComments);
491  IO.mapOptional("SortIncludes", Style.SortIncludes);
492  IO.mapOptional("SortUsingDeclarations", Style.SortUsingDeclarations);
493  IO.mapOptional("SpaceAfterCStyleCast", Style.SpaceAfterCStyleCast);
494  IO.mapOptional("SpaceAfterLogicalNot", Style.SpaceAfterLogicalNot);
495  IO.mapOptional("SpaceAfterTemplateKeyword",
496  Style.SpaceAfterTemplateKeyword);
497  IO.mapOptional("SpaceBeforeAssignmentOperators",
498  Style.SpaceBeforeAssignmentOperators);
499  IO.mapOptional("SpaceBeforeCpp11BracedList",
500  Style.SpaceBeforeCpp11BracedList);
501  IO.mapOptional("SpaceBeforeCtorInitializerColon",
502  Style.SpaceBeforeCtorInitializerColon);
503  IO.mapOptional("SpaceBeforeInheritanceColon",
504  Style.SpaceBeforeInheritanceColon);
505  IO.mapOptional("SpaceBeforeParens", Style.SpaceBeforeParens);
506  IO.mapOptional("SpaceBeforeRangeBasedForLoopColon",
507  Style.SpaceBeforeRangeBasedForLoopColon);
508  IO.mapOptional("SpaceInEmptyBlock", Style.SpaceInEmptyBlock);
509  IO.mapOptional("SpaceInEmptyParentheses", Style.SpaceInEmptyParentheses);
510  IO.mapOptional("SpacesBeforeTrailingComments",
511  Style.SpacesBeforeTrailingComments);
512  IO.mapOptional("SpacesInAngles", Style.SpacesInAngles);
513  IO.mapOptional("SpacesInContainerLiterals",
514  Style.SpacesInContainerLiterals);
515  IO.mapOptional("SpacesInCStyleCastParentheses",
516  Style.SpacesInCStyleCastParentheses);
517  IO.mapOptional("SpacesInParentheses", Style.SpacesInParentheses);
518  IO.mapOptional("SpacesInSquareBrackets", Style.SpacesInSquareBrackets);
519  IO.mapOptional("Standard", Style.Standard);
520  IO.mapOptional("StatementMacros", Style.StatementMacros);
521  IO.mapOptional("TabWidth", Style.TabWidth);
522  IO.mapOptional("TypenameMacros", Style.TypenameMacros);
523  IO.mapOptional("UseTab", Style.UseTab);
524  }
525 };
526 
527 template <> struct MappingTraits<FormatStyle::BraceWrappingFlags> {
528  static void mapping(IO &IO, FormatStyle::BraceWrappingFlags &Wrapping) {
529  IO.mapOptional("AfterCaseLabel", Wrapping.AfterCaseLabel);
530  IO.mapOptional("AfterClass", Wrapping.AfterClass);
531  IO.mapOptional("AfterControlStatement", Wrapping.AfterControlStatement);
532  IO.mapOptional("AfterEnum", Wrapping.AfterEnum);
533  IO.mapOptional("AfterFunction", Wrapping.AfterFunction);
534  IO.mapOptional("AfterNamespace", Wrapping.AfterNamespace);
535  IO.mapOptional("AfterObjCDeclaration", Wrapping.AfterObjCDeclaration);
536  IO.mapOptional("AfterStruct", Wrapping.AfterStruct);
537  IO.mapOptional("AfterUnion", Wrapping.AfterUnion);
538  IO.mapOptional("AfterExternBlock", Wrapping.AfterExternBlock);
539  IO.mapOptional("BeforeCatch", Wrapping.BeforeCatch);
540  IO.mapOptional("BeforeElse", Wrapping.BeforeElse);
541  IO.mapOptional("IndentBraces", Wrapping.IndentBraces);
542  IO.mapOptional("SplitEmptyFunction", Wrapping.SplitEmptyFunction);
543  IO.mapOptional("SplitEmptyRecord", Wrapping.SplitEmptyRecord);
544  IO.mapOptional("SplitEmptyNamespace", Wrapping.SplitEmptyNamespace);
545  }
546 };
547 
548 template <> struct MappingTraits<FormatStyle::RawStringFormat> {
549  static void mapping(IO &IO, FormatStyle::RawStringFormat &Format) {
550  IO.mapOptional("Language", Format.Language);
551  IO.mapOptional("Delimiters", Format.Delimiters);
552  IO.mapOptional("EnclosingFunctions", Format.EnclosingFunctions);
553  IO.mapOptional("CanonicalDelimiter", Format.CanonicalDelimiter);
554  IO.mapOptional("BasedOnStyle", Format.BasedOnStyle);
555  }
556 };
557 
558 // Allows to read vector<FormatStyle> while keeping default values.
559 // IO.getContext() should contain a pointer to the FormatStyle structure, that
560 // will be used to get default values for missing keys.
561 // If the first element has no Language specified, it will be treated as the
562 // default one for the following elements.
563 template <> struct DocumentListTraits<std::vector<FormatStyle>> {
564  static size_t size(IO &IO, std::vector<FormatStyle> &Seq) {
565  return Seq.size();
566  }
567  static FormatStyle &element(IO &IO, std::vector<FormatStyle> &Seq,
568  size_t Index) {
569  if (Index >= Seq.size()) {
570  assert(Index == Seq.size());
571  FormatStyle Template;
572  if (!Seq.empty() && Seq[0].Language == FormatStyle::LK_None) {
573  Template = Seq[0];
574  } else {
575  Template = *((const FormatStyle *)IO.getContext());
576  Template.Language = FormatStyle::LK_None;
577  }
578  Seq.resize(Index + 1, Template);
579  }
580  return Seq[Index];
581  }
582 };
583 } // namespace yaml
584 } // namespace llvm
585 
586 namespace clang {
587 namespace format {
588 
589 const std::error_category &getParseCategory() {
590  static const ParseErrorCategory C{};
591  return C;
592 }
593 std::error_code make_error_code(ParseError e) {
594  return std::error_code(static_cast<int>(e), getParseCategory());
595 }
596 
597 inline llvm::Error make_string_error(const llvm::Twine &Message) {
598  return llvm::make_error<llvm::StringError>(Message,
599  llvm::inconvertibleErrorCode());
600 }
601 
602 const char *ParseErrorCategory::name() const noexcept {
603  return "clang-format.parse_error";
604 }
605 
606 std::string ParseErrorCategory::message(int EV) const {
607  switch (static_cast<ParseError>(EV)) {
608  case ParseError::Success:
609  return "Success";
610  case ParseError::Error:
611  return "Invalid argument";
612  case ParseError::Unsuitable:
613  return "Unsuitable";
614  }
615  llvm_unreachable("unexpected parse error");
616 }
617 
619  if (Style.BreakBeforeBraces == FormatStyle::BS_Custom)
620  return Style;
621  FormatStyle Expanded = Style;
622  Expanded.BraceWrapping = {false, false, false, false, false, false,
623  false, false, false, false, false, false,
624  false, true, true, true};
625  switch (Style.BreakBeforeBraces) {
626  case FormatStyle::BS_Linux:
627  Expanded.BraceWrapping.AfterClass = true;
628  Expanded.BraceWrapping.AfterFunction = true;
629  Expanded.BraceWrapping.AfterNamespace = true;
630  break;
631  case FormatStyle::BS_Mozilla:
632  Expanded.BraceWrapping.AfterClass = true;
633  Expanded.BraceWrapping.AfterEnum = true;
634  Expanded.BraceWrapping.AfterFunction = true;
635  Expanded.BraceWrapping.AfterStruct = true;
636  Expanded.BraceWrapping.AfterUnion = true;
637  Expanded.BraceWrapping.AfterExternBlock = true;
638  Expanded.BraceWrapping.SplitEmptyFunction = true;
639  Expanded.BraceWrapping.SplitEmptyRecord = false;
640  break;
641  case FormatStyle::BS_Stroustrup:
642  Expanded.BraceWrapping.AfterFunction = true;
643  Expanded.BraceWrapping.BeforeCatch = true;
644  Expanded.BraceWrapping.BeforeElse = true;
645  break;
646  case FormatStyle::BS_Allman:
647  Expanded.BraceWrapping.AfterCaseLabel = true;
648  Expanded.BraceWrapping.AfterClass = true;
649  Expanded.BraceWrapping.AfterControlStatement = true;
650  Expanded.BraceWrapping.AfterEnum = true;
651  Expanded.BraceWrapping.AfterFunction = true;
652  Expanded.BraceWrapping.AfterNamespace = true;
653  Expanded.BraceWrapping.AfterObjCDeclaration = true;
654  Expanded.BraceWrapping.AfterStruct = true;
655  Expanded.BraceWrapping.AfterUnion = true;
656  Expanded.BraceWrapping.AfterExternBlock = true;
657  Expanded.BraceWrapping.BeforeCatch = true;
658  Expanded.BraceWrapping.BeforeElse = true;
659  break;
660  case FormatStyle::BS_GNU:
661  Expanded.BraceWrapping = {true, true, true, true, true, true, true, true,
662  true, true, true, true, true, true, true, true};
663  break;
664  case FormatStyle::BS_WebKit:
665  Expanded.BraceWrapping.AfterFunction = true;
666  break;
667  default:
668  break;
669  }
670  return Expanded;
671 }
672 
673 FormatStyle getLLVMStyle(FormatStyle::LanguageKind Language) {
674  FormatStyle LLVMStyle;
675  LLVMStyle.Language = Language;
676  LLVMStyle.AccessModifierOffset = -2;
677  LLVMStyle.AlignEscapedNewlines = FormatStyle::ENAS_Right;
678  LLVMStyle.AlignAfterOpenBracket = FormatStyle::BAS_Align;
679  LLVMStyle.AlignOperands = true;
680  LLVMStyle.AlignTrailingComments = true;
681  LLVMStyle.AlignConsecutiveAssignments = false;
682  LLVMStyle.AlignConsecutiveDeclarations = false;
683  LLVMStyle.AlignConsecutiveMacros = false;
684  LLVMStyle.AllowAllArgumentsOnNextLine = true;
685  LLVMStyle.AllowAllConstructorInitializersOnNextLine = true;
686  LLVMStyle.AllowAllParametersOfDeclarationOnNextLine = true;
687  LLVMStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_All;
688  LLVMStyle.AllowShortBlocksOnASingleLine = FormatStyle::SBS_Never;
689  LLVMStyle.AllowShortCaseLabelsOnASingleLine = false;
690  LLVMStyle.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_Never;
691  LLVMStyle.AllowShortLambdasOnASingleLine = FormatStyle::SLS_All;
692  LLVMStyle.AllowShortLoopsOnASingleLine = false;
693  LLVMStyle.AlwaysBreakAfterReturnType = FormatStyle::RTBS_None;
694  LLVMStyle.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_None;
695  LLVMStyle.AlwaysBreakBeforeMultilineStrings = false;
696  LLVMStyle.AlwaysBreakTemplateDeclarations = FormatStyle::BTDS_MultiLine;
697  LLVMStyle.BinPackArguments = true;
698  LLVMStyle.BinPackParameters = true;
699  LLVMStyle.BreakBeforeBinaryOperators = FormatStyle::BOS_None;
700  LLVMStyle.BreakBeforeTernaryOperators = true;
701  LLVMStyle.BreakBeforeBraces = FormatStyle::BS_Attach;
702  LLVMStyle.BraceWrapping = {false, false, false, false, false, false,
703  false, false, false, false, false, false,
704  false, true, true, true};
705  LLVMStyle.BreakAfterJavaFieldAnnotations = false;
706  LLVMStyle.BreakConstructorInitializers = FormatStyle::BCIS_BeforeColon;
707  LLVMStyle.BreakInheritanceList = FormatStyle::BILS_BeforeColon;
708  LLVMStyle.BreakStringLiterals = true;
709  LLVMStyle.ColumnLimit = 80;
710  LLVMStyle.CommentPragmas = "^ IWYU pragma:";
711  LLVMStyle.CompactNamespaces = false;
712  LLVMStyle.ConstructorInitializerAllOnOneLineOrOnePerLine = false;
713  LLVMStyle.ConstructorInitializerIndentWidth = 4;
714  LLVMStyle.ContinuationIndentWidth = 4;
715  LLVMStyle.Cpp11BracedListStyle = true;
716  LLVMStyle.DerivePointerAlignment = false;
717  LLVMStyle.ExperimentalAutoDetectBinPacking = false;
718  LLVMStyle.FixNamespaceComments = true;
719  LLVMStyle.ForEachMacros.push_back("foreach");
720  LLVMStyle.ForEachMacros.push_back("Q_FOREACH");
721  LLVMStyle.ForEachMacros.push_back("BOOST_FOREACH");
722  LLVMStyle.IncludeStyle.IncludeCategories = {
723  {"^\"(llvm|llvm-c|clang|clang-c)/", 2},
724  {"^(<|\"(gtest|gmock|isl|json)/)", 3},
725  {".*", 1}};
726  LLVMStyle.IncludeStyle.IncludeIsMainRegex = "(Test)?$";
727  LLVMStyle.IncludeStyle.IncludeBlocks = tooling::IncludeStyle::IBS_Preserve;
728  LLVMStyle.IndentCaseLabels = false;
729  LLVMStyle.IndentGotoLabels = true;
730  LLVMStyle.IndentPPDirectives = FormatStyle::PPDIS_None;
731  LLVMStyle.IndentWrappedFunctionNames = false;
732  LLVMStyle.IndentWidth = 2;
733  LLVMStyle.JavaScriptQuotes = FormatStyle::JSQS_Leave;
734  LLVMStyle.JavaScriptWrapImports = true;
735  LLVMStyle.TabWidth = 8;
736  LLVMStyle.MaxEmptyLinesToKeep = 1;
737  LLVMStyle.KeepEmptyLinesAtTheStartOfBlocks = true;
738  LLVMStyle.NamespaceIndentation = FormatStyle::NI_None;
739  LLVMStyle.ObjCBinPackProtocolList = FormatStyle::BPS_Auto;
740  LLVMStyle.ObjCBlockIndentWidth = 2;
741  LLVMStyle.ObjCSpaceAfterProperty = false;
742  LLVMStyle.ObjCSpaceBeforeProtocolList = true;
743  LLVMStyle.PointerAlignment = FormatStyle::PAS_Right;
744  LLVMStyle.SpacesBeforeTrailingComments = 1;
745  LLVMStyle.Standard = FormatStyle::LS_Cpp11;
746  LLVMStyle.UseTab = FormatStyle::UT_Never;
747  LLVMStyle.ReflowComments = true;
748  LLVMStyle.SpacesInParentheses = false;
749  LLVMStyle.SpacesInSquareBrackets = false;
750  LLVMStyle.SpaceInEmptyBlock = false;
751  LLVMStyle.SpaceInEmptyParentheses = false;
752  LLVMStyle.SpacesInContainerLiterals = true;
753  LLVMStyle.SpacesInCStyleCastParentheses = false;
754  LLVMStyle.SpaceAfterCStyleCast = false;
755  LLVMStyle.SpaceAfterLogicalNot = false;
756  LLVMStyle.SpaceAfterTemplateKeyword = true;
757  LLVMStyle.SpaceBeforeCtorInitializerColon = true;
758  LLVMStyle.SpaceBeforeInheritanceColon = true;
759  LLVMStyle.SpaceBeforeParens = FormatStyle::SBPO_ControlStatements;
760  LLVMStyle.SpaceBeforeRangeBasedForLoopColon = true;
761  LLVMStyle.SpaceBeforeAssignmentOperators = true;
762  LLVMStyle.SpaceBeforeCpp11BracedList = false;
763  LLVMStyle.SpacesInAngles = false;
764 
765  LLVMStyle.PenaltyBreakAssignment = prec::Assignment;
766  LLVMStyle.PenaltyBreakComment = 300;
767  LLVMStyle.PenaltyBreakFirstLessLess = 120;
768  LLVMStyle.PenaltyBreakString = 1000;
769  LLVMStyle.PenaltyExcessCharacter = 1000000;
770  LLVMStyle.PenaltyReturnTypeOnItsOwnLine = 60;
771  LLVMStyle.PenaltyBreakBeforeFirstCallParameter = 19;
772  LLVMStyle.PenaltyBreakTemplateDeclaration = prec::Relational;
773 
774  LLVMStyle.DisableFormat = false;
775  LLVMStyle.SortIncludes = true;
776  LLVMStyle.SortUsingDeclarations = true;
777  LLVMStyle.StatementMacros.push_back("Q_UNUSED");
778  LLVMStyle.StatementMacros.push_back("QT_REQUIRE_VERSION");
779 
780  // Defaults that differ when not C++.
781  if (Language == FormatStyle::LK_TableGen) {
782  LLVMStyle.SpacesInContainerLiterals = false;
783  }
784 
785  return LLVMStyle;
786 }
787 
788 FormatStyle getGoogleStyle(FormatStyle::LanguageKind Language) {
789  if (Language == FormatStyle::LK_TextProto) {
790  FormatStyle GoogleStyle = getGoogleStyle(FormatStyle::LK_Proto);
791  GoogleStyle.Language = FormatStyle::LK_TextProto;
792 
793  return GoogleStyle;
794  }
795 
796  FormatStyle GoogleStyle = getLLVMStyle(Language);
797 
798  GoogleStyle.AccessModifierOffset = -1;
799  GoogleStyle.AlignEscapedNewlines = FormatStyle::ENAS_Left;
800  GoogleStyle.AllowShortIfStatementsOnASingleLine =
801  FormatStyle::SIS_WithoutElse;
802  GoogleStyle.AllowShortLoopsOnASingleLine = true;
803  GoogleStyle.AlwaysBreakBeforeMultilineStrings = true;
804  GoogleStyle.AlwaysBreakTemplateDeclarations = FormatStyle::BTDS_Yes;
805  GoogleStyle.ConstructorInitializerAllOnOneLineOrOnePerLine = true;
806  GoogleStyle.DerivePointerAlignment = true;
807  GoogleStyle.IncludeStyle.IncludeCategories = {
808  {"^<ext/.*\\.h>", 2}, {"^<.*\\.h>", 1}, {"^<.*", 2}, {".*", 3}};
809  GoogleStyle.IncludeStyle.IncludeIsMainRegex = "([-_](test|unittest))?$";
810  GoogleStyle.IncludeStyle.IncludeBlocks = tooling::IncludeStyle::IBS_Regroup;
811  GoogleStyle.IndentCaseLabels = true;
812  GoogleStyle.KeepEmptyLinesAtTheStartOfBlocks = false;
813  GoogleStyle.ObjCBinPackProtocolList = FormatStyle::BPS_Never;
814  GoogleStyle.ObjCSpaceAfterProperty = false;
815  GoogleStyle.ObjCSpaceBeforeProtocolList = true;
816  GoogleStyle.PointerAlignment = FormatStyle::PAS_Left;
817  GoogleStyle.RawStringFormats = {
818  {
819  FormatStyle::LK_Cpp,
820  /*Delimiters=*/
821  {
822  "cc",
823  "CC",
824  "cpp",
825  "Cpp",
826  "CPP",
827  "c++",
828  "C++",
829  },
830  /*EnclosingFunctionNames=*/
831  {},
832  /*CanonicalDelimiter=*/"",
833  /*BasedOnStyle=*/"google",
834  },
835  {
836  FormatStyle::LK_TextProto,
837  /*Delimiters=*/
838  {
839  "pb",
840  "PB",
841  "proto",
842  "PROTO",
843  },
844  /*EnclosingFunctionNames=*/
845  {
846  "EqualsProto",
847  "EquivToProto",
848  "PARSE_PARTIAL_TEXT_PROTO",
849  "PARSE_TEST_PROTO",
850  "PARSE_TEXT_PROTO",
851  "ParseTextOrDie",
852  "ParseTextProtoOrDie",
853  },
854  /*CanonicalDelimiter=*/"",
855  /*BasedOnStyle=*/"google",
856  },
857  };
858  GoogleStyle.SpacesBeforeTrailingComments = 2;
859  GoogleStyle.Standard = FormatStyle::LS_Auto;
860 
861  GoogleStyle.PenaltyReturnTypeOnItsOwnLine = 200;
862  GoogleStyle.PenaltyBreakBeforeFirstCallParameter = 1;
863 
864  if (Language == FormatStyle::LK_Java) {
865  GoogleStyle.AlignAfterOpenBracket = FormatStyle::BAS_DontAlign;
866  GoogleStyle.AlignOperands = false;
867  GoogleStyle.AlignTrailingComments = false;
868  GoogleStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Empty;
869  GoogleStyle.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_Never;
870  GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
871  GoogleStyle.BreakBeforeBinaryOperators = FormatStyle::BOS_NonAssignment;
872  GoogleStyle.ColumnLimit = 100;
873  GoogleStyle.SpaceAfterCStyleCast = true;
874  GoogleStyle.SpacesBeforeTrailingComments = 1;
875  } else if (Language == FormatStyle::LK_JavaScript) {
876  GoogleStyle.AlignAfterOpenBracket = FormatStyle::BAS_AlwaysBreak;
877  GoogleStyle.AlignOperands = false;
878  GoogleStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Empty;
879  GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
880  GoogleStyle.BreakBeforeTernaryOperators = false;
881  // taze:, triple slash directives (`/// <...`), @see, which is commonly
882  // followed by overlong URLs.
883  GoogleStyle.CommentPragmas = "(taze:|^/[ \t]*<|@see)";
884  GoogleStyle.MaxEmptyLinesToKeep = 3;
885  GoogleStyle.NamespaceIndentation = FormatStyle::NI_All;
886  GoogleStyle.SpacesInContainerLiterals = false;
887  GoogleStyle.JavaScriptQuotes = FormatStyle::JSQS_Single;
888  GoogleStyle.JavaScriptWrapImports = false;
889  } else if (Language == FormatStyle::LK_Proto) {
890  GoogleStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Empty;
891  GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
892  GoogleStyle.SpacesInContainerLiterals = false;
893  GoogleStyle.Cpp11BracedListStyle = false;
894  // This affects protocol buffer options specifications and text protos.
895  // Text protos are currently mostly formatted inside C++ raw string literals
896  // and often the current breaking behavior of string literals is not
897  // beneficial there. Investigate turning this on once proper string reflow
898  // has been implemented.
899  GoogleStyle.BreakStringLiterals = false;
900  } else if (Language == FormatStyle::LK_ObjC) {
901  GoogleStyle.AlwaysBreakBeforeMultilineStrings = false;
902  GoogleStyle.ColumnLimit = 100;
903  // "Regroup" doesn't work well for ObjC yet (main header heuristic,
904  // relationship between ObjC standard library headers and other heades,
905  // #imports, etc.)
906  GoogleStyle.IncludeStyle.IncludeBlocks =
907  tooling::IncludeStyle::IBS_Preserve;
908  }
909 
910  return GoogleStyle;
911 }
912 
913 FormatStyle getChromiumStyle(FormatStyle::LanguageKind Language) {
914  FormatStyle ChromiumStyle = getGoogleStyle(Language);
915 
916  // Disable include reordering across blocks in Chromium code.
917  // - clang-format tries to detect that foo.h is the "main" header for
918  // foo.cc and foo_unittest.cc via IncludeIsMainRegex. However, Chromium
919  // uses many other suffices (_win.cc, _mac.mm, _posix.cc, _browsertest.cc,
920  // _private.cc, _impl.cc etc) in different permutations
921  // (_win_browsertest.cc) so disable this until IncludeIsMainRegex has a
922  // better default for Chromium code.
923  // - The default for .cc and .mm files is different (r357695) for Google style
924  // for the same reason. The plan is to unify this again once the main
925  // header detection works for Google's ObjC code, but this hasn't happened
926  // yet. Since Chromium has some ObjC code, switching Chromium is blocked
927  // on that.
928  // - Finally, "If include reordering is harmful, put things in different
929  // blocks to prevent it" has been a recommendation for a long time that
930  // people are used to. We'll need a dev education push to change this to
931  // "If include reordering is harmful, put things in a different block and
932  // _prepend that with a comment_ to prevent it" before changing behavior.
933  ChromiumStyle.IncludeStyle.IncludeBlocks =
934  tooling::IncludeStyle::IBS_Preserve;
935 
936  if (Language == FormatStyle::LK_Java) {
937  ChromiumStyle.AllowShortIfStatementsOnASingleLine =
938  FormatStyle::SIS_WithoutElse;
939  ChromiumStyle.BreakAfterJavaFieldAnnotations = true;
940  ChromiumStyle.ContinuationIndentWidth = 8;
941  ChromiumStyle.IndentWidth = 4;
942  // See styleguide for import groups:
943  // https://chromium.googlesource.com/chromium/src/+/master/styleguide/java/java.md#Import-Order
944  ChromiumStyle.JavaImportGroups = {
945  "android",
946  "androidx",
947  "com",
948  "dalvik",
949  "junit",
950  "org",
951  "com.google.android.apps.chrome",
952  "org.chromium",
953  "java",
954  "javax",
955  };
956  ChromiumStyle.SortIncludes = true;
957  } else if (Language == FormatStyle::LK_JavaScript) {
958  ChromiumStyle.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_Never;
959  ChromiumStyle.AllowShortLoopsOnASingleLine = false;
960  } else {
961  ChromiumStyle.AllowAllParametersOfDeclarationOnNextLine = false;
962  ChromiumStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Inline;
963  ChromiumStyle.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_Never;
964  ChromiumStyle.AllowShortLoopsOnASingleLine = false;
965  ChromiumStyle.BinPackParameters = false;
966  ChromiumStyle.DerivePointerAlignment = false;
967  if (Language == FormatStyle::LK_ObjC)
968  ChromiumStyle.ColumnLimit = 80;
969  }
970  return ChromiumStyle;
971 }
972 
974  FormatStyle MozillaStyle = getLLVMStyle();
975  MozillaStyle.AllowAllParametersOfDeclarationOnNextLine = false;
976  MozillaStyle.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_Inline;
977  MozillaStyle.AlwaysBreakAfterReturnType = FormatStyle::RTBS_TopLevel;
978  MozillaStyle.AlwaysBreakAfterDefinitionReturnType =
979  FormatStyle::DRTBS_TopLevel;
980  MozillaStyle.AlwaysBreakTemplateDeclarations = FormatStyle::BTDS_Yes;
981  MozillaStyle.BinPackParameters = false;
982  MozillaStyle.BinPackArguments = false;
983  MozillaStyle.BreakBeforeBraces = FormatStyle::BS_Mozilla;
984  MozillaStyle.BreakConstructorInitializers = FormatStyle::BCIS_BeforeComma;
985  MozillaStyle.BreakInheritanceList = FormatStyle::BILS_BeforeComma;
986  MozillaStyle.ConstructorInitializerIndentWidth = 2;
987  MozillaStyle.ContinuationIndentWidth = 2;
988  MozillaStyle.Cpp11BracedListStyle = false;
989  MozillaStyle.FixNamespaceComments = false;
990  MozillaStyle.IndentCaseLabels = true;
991  MozillaStyle.ObjCSpaceAfterProperty = true;
992  MozillaStyle.ObjCSpaceBeforeProtocolList = false;
993  MozillaStyle.PenaltyReturnTypeOnItsOwnLine = 200;
994  MozillaStyle.PointerAlignment = FormatStyle::PAS_Left;
995  MozillaStyle.SpaceAfterTemplateKeyword = false;
996  return MozillaStyle;
997 }
998 
1001  Style.AccessModifierOffset = -4;
1002  Style.AlignAfterOpenBracket = FormatStyle::BAS_DontAlign;
1003  Style.AlignOperands = false;
1004  Style.AlignTrailingComments = false;
1005  Style.AllowShortBlocksOnASingleLine = FormatStyle::SBS_Empty;
1006  Style.BreakBeforeBinaryOperators = FormatStyle::BOS_All;
1007  Style.BreakBeforeBraces = FormatStyle::BS_WebKit;
1008  Style.BreakConstructorInitializers = FormatStyle::BCIS_BeforeComma;
1009  Style.Cpp11BracedListStyle = false;
1010  Style.ColumnLimit = 0;
1011  Style.FixNamespaceComments = false;
1012  Style.IndentWidth = 4;
1013  Style.NamespaceIndentation = FormatStyle::NI_Inner;
1014  Style.ObjCBlockIndentWidth = 4;
1015  Style.ObjCSpaceAfterProperty = true;
1016  Style.PointerAlignment = FormatStyle::PAS_Left;
1017  Style.SpaceBeforeCpp11BracedList = true;
1018  Style.SpaceInEmptyBlock = true;
1019  return Style;
1020 }
1021 
1024  Style.AlwaysBreakAfterDefinitionReturnType = FormatStyle::DRTBS_All;
1025  Style.AlwaysBreakAfterReturnType = FormatStyle::RTBS_AllDefinitions;
1026  Style.BreakBeforeBinaryOperators = FormatStyle::BOS_All;
1027  Style.BreakBeforeBraces = FormatStyle::BS_GNU;
1028  Style.BreakBeforeTernaryOperators = true;
1029  Style.Cpp11BracedListStyle = false;
1030  Style.ColumnLimit = 79;
1031  Style.FixNamespaceComments = false;
1032  Style.SpaceBeforeParens = FormatStyle::SBPO_Always;
1033  Style.Standard = FormatStyle::LS_Cpp03;
1034  return Style;
1035 }
1036 
1037 FormatStyle getMicrosoftStyle(FormatStyle::LanguageKind Language) {
1039  Style.ColumnLimit = 120;
1040  Style.TabWidth = 4;
1041  Style.IndentWidth = 4;
1042  Style.UseTab = FormatStyle::UT_Never;
1043  Style.BreakBeforeBraces = FormatStyle::BS_Custom;
1044  Style.BraceWrapping.AfterClass = true;
1045  Style.BraceWrapping.AfterControlStatement = true;
1046  Style.BraceWrapping.AfterEnum = true;
1047  Style.BraceWrapping.AfterFunction = true;
1048  Style.BraceWrapping.AfterNamespace = true;
1049  Style.BraceWrapping.AfterObjCDeclaration = true;
1050  Style.BraceWrapping.AfterStruct = true;
1051  Style.BraceWrapping.AfterExternBlock = true;
1052  Style.BraceWrapping.BeforeCatch = true;
1053  Style.BraceWrapping.BeforeElse = true;
1054  Style.PenaltyReturnTypeOnItsOwnLine = 1000;
1055  Style.AllowShortFunctionsOnASingleLine = FormatStyle::SFS_None;
1056  Style.AllowShortCaseLabelsOnASingleLine = false;
1057  Style.AllowShortIfStatementsOnASingleLine = FormatStyle::SIS_Never;
1058  Style.AllowShortLoopsOnASingleLine = false;
1059  return Style;
1060 }
1061 
1063  FormatStyle NoStyle = getLLVMStyle();
1064  NoStyle.DisableFormat = true;
1065  NoStyle.SortIncludes = false;
1066  NoStyle.SortUsingDeclarations = false;
1067  return NoStyle;
1068 }
1069 
1070 bool getPredefinedStyle(StringRef Name, FormatStyle::LanguageKind Language,
1071  FormatStyle *Style) {
1072  if (Name.equals_lower("llvm")) {
1073  *Style = getLLVMStyle(Language);
1074  } else if (Name.equals_lower("chromium")) {
1075  *Style = getChromiumStyle(Language);
1076  } else if (Name.equals_lower("mozilla")) {
1077  *Style = getMozillaStyle();
1078  } else if (Name.equals_lower("google")) {
1079  *Style = getGoogleStyle(Language);
1080  } else if (Name.equals_lower("webkit")) {
1081  *Style = getWebKitStyle();
1082  } else if (Name.equals_lower("gnu")) {
1083  *Style = getGNUStyle();
1084  } else if (Name.equals_lower("microsoft")) {
1085  *Style = getMicrosoftStyle(Language);
1086  } else if (Name.equals_lower("none")) {
1087  *Style = getNoStyle();
1088  } else {
1089  return false;
1090  }
1091 
1092  Style->Language = Language;
1093  return true;
1094 }
1095 
1096 std::error_code parseConfiguration(StringRef Text, FormatStyle *Style) {
1097  assert(Style);
1098  FormatStyle::LanguageKind Language = Style->Language;
1099  assert(Language != FormatStyle::LK_None);
1100  if (Text.trim().empty())
1102  Style->StyleSet.Clear();
1103  std::vector<FormatStyle> Styles;
1104  llvm::yaml::Input Input(Text);
1105  // DocumentListTraits<vector<FormatStyle>> uses the context to get default
1106  // values for the fields, keys for which are missing from the configuration.
1107  // Mapping also uses the context to get the language to find the correct
1108  // base style.
1109  Input.setContext(Style);
1110  Input >> Styles;
1111  if (Input.error())
1112  return Input.error();
1113 
1114  for (unsigned i = 0; i < Styles.size(); ++i) {
1115  // Ensures that only the first configuration can skip the Language option.
1116  if (Styles[i].Language == FormatStyle::LK_None && i != 0)
1118  // Ensure that each language is configured at most once.
1119  for (unsigned j = 0; j < i; ++j) {
1120  if (Styles[i].Language == Styles[j].Language) {
1121  LLVM_DEBUG(llvm::dbgs()
1122  << "Duplicate languages in the config file on positions "
1123  << j << " and " << i << "\n");
1125  }
1126  }
1127  }
1128  // Look for a suitable configuration starting from the end, so we can
1129  // find the configuration for the specific language first, and the default
1130  // configuration (which can only be at slot 0) after it.
1131  FormatStyle::FormatStyleSet StyleSet;
1132  bool LanguageFound = false;
1133  for (int i = Styles.size() - 1; i >= 0; --i) {
1134  if (Styles[i].Language != FormatStyle::LK_None)
1135  StyleSet.Add(Styles[i]);
1136  if (Styles[i].Language == Language)
1137  LanguageFound = true;
1138  }
1139  if (!LanguageFound) {
1140  if (Styles.empty() || Styles[0].Language != FormatStyle::LK_None)
1141  return make_error_code(ParseError::Unsuitable);
1142  FormatStyle DefaultStyle = Styles[0];
1143  DefaultStyle.Language = Language;
1144  StyleSet.Add(std::move(DefaultStyle));
1145  }
1146  *Style = *StyleSet.Get(Language);
1147  return make_error_code(ParseError::Success);
1148 }
1149 
1151  std::string Text;
1152  llvm::raw_string_ostream Stream(Text);
1153  llvm::yaml::Output Output(Stream);
1154  // We use the same mapping method for input and output, so we need a non-const
1155  // reference here.
1156  FormatStyle NonConstStyle = expandPresets(Style);
1157  Output << NonConstStyle;
1158  return Stream.str();
1159 }
1160 
1162 FormatStyle::FormatStyleSet::Get(FormatStyle::LanguageKind Language) const {
1163  if (!Styles)
1164  return None;
1165  auto It = Styles->find(Language);
1166  if (It == Styles->end())
1167  return None;
1168  FormatStyle Style = It->second;
1169  Style.StyleSet = *this;
1170  return Style;
1171 }
1172 
1174  assert(Style.Language != LK_None &&
1175  "Cannot add a style for LK_None to a StyleSet");
1176  assert(
1177  !Style.StyleSet.Styles &&
1178  "Cannot add a style associated with an existing StyleSet to a StyleSet");
1179  if (!Styles)
1180  Styles = std::make_shared<MapType>();
1181  (*Styles)[Style.Language] = std::move(Style);
1182 }
1183 
1184 void FormatStyle::FormatStyleSet::Clear() { Styles.reset(); }
1185 
1187 FormatStyle::GetLanguageStyle(FormatStyle::LanguageKind Language) const {
1188  return StyleSet.Get(Language);
1189 }
1190 
1191 namespace {
1192 
1193 class JavaScriptRequoter : public TokenAnalyzer {
1194 public:
1195  JavaScriptRequoter(const Environment &Env, const FormatStyle &Style)
1196  : TokenAnalyzer(Env, Style) {}
1197 
1198  std::pair<tooling::Replacements, unsigned>
1199  analyze(TokenAnnotator &Annotator,
1200  SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1201  FormatTokenLexer &Tokens) override {
1202  AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
1203  tooling::Replacements Result;
1204  requoteJSStringLiteral(AnnotatedLines, Result);
1205  return {Result, 0};
1206  }
1207 
1208 private:
1209  // Replaces double/single-quoted string literal as appropriate, re-escaping
1210  // the contents in the process.
1211  void requoteJSStringLiteral(SmallVectorImpl<AnnotatedLine *> &Lines,
1212  tooling::Replacements &Result) {
1213  for (AnnotatedLine *Line : Lines) {
1214  requoteJSStringLiteral(Line->Children, Result);
1215  if (!Line->Affected)
1216  continue;
1217  for (FormatToken *FormatTok = Line->First; FormatTok;
1218  FormatTok = FormatTok->Next) {
1219  StringRef Input = FormatTok->TokenText;
1220  if (FormatTok->Finalized || !FormatTok->isStringLiteral() ||
1221  // NB: testing for not starting with a double quote to avoid
1222  // breaking `template strings`.
1223  (Style.JavaScriptQuotes == FormatStyle::JSQS_Single &&
1224  !Input.startswith("\"")) ||
1225  (Style.JavaScriptQuotes == FormatStyle::JSQS_Double &&
1226  !Input.startswith("\'")))
1227  continue;
1228 
1229  // Change start and end quote.
1230  bool IsSingle = Style.JavaScriptQuotes == FormatStyle::JSQS_Single;
1231  SourceLocation Start = FormatTok->Tok.getLocation();
1232  auto Replace = [&](SourceLocation Start, unsigned Length,
1233  StringRef ReplacementText) {
1234  auto Err = Result.add(tooling::Replacement(
1235  Env.getSourceManager(), Start, Length, ReplacementText));
1236  // FIXME: handle error. For now, print error message and skip the
1237  // replacement for release version.
1238  if (Err) {
1239  llvm::errs() << llvm::toString(std::move(Err)) << "\n";
1240  assert(false);
1241  }
1242  };
1243  Replace(Start, 1, IsSingle ? "'" : "\"");
1244  Replace(FormatTok->Tok.getEndLoc().getLocWithOffset(-1), 1,
1245  IsSingle ? "'" : "\"");
1246 
1247  // Escape internal quotes.
1248  bool Escaped = false;
1249  for (size_t i = 1; i < Input.size() - 1; i++) {
1250  switch (Input[i]) {
1251  case '\\':
1252  if (!Escaped && i + 1 < Input.size() &&
1253  ((IsSingle && Input[i + 1] == '"') ||
1254  (!IsSingle && Input[i + 1] == '\''))) {
1255  // Remove this \, it's escaping a " or ' that no longer needs
1256  // escaping
1257  Replace(Start.getLocWithOffset(i), 1, "");
1258  continue;
1259  }
1260  Escaped = !Escaped;
1261  break;
1262  case '\"':
1263  case '\'':
1264  if (!Escaped && IsSingle == (Input[i] == '\'')) {
1265  // Escape the quote.
1266  Replace(Start.getLocWithOffset(i), 0, "\\");
1267  }
1268  Escaped = false;
1269  break;
1270  default:
1271  Escaped = false;
1272  break;
1273  }
1274  }
1275  }
1276  }
1277  }
1278 };
1279 
1280 class Formatter : public TokenAnalyzer {
1281 public:
1282  Formatter(const Environment &Env, const FormatStyle &Style,
1283  FormattingAttemptStatus *Status)
1284  : TokenAnalyzer(Env, Style), Status(Status) {}
1285 
1286  std::pair<tooling::Replacements, unsigned>
1287  analyze(TokenAnnotator &Annotator,
1288  SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1289  FormatTokenLexer &Tokens) override {
1290  tooling::Replacements Result;
1291  deriveLocalStyle(AnnotatedLines);
1292  AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
1293  for (unsigned i = 0, e = AnnotatedLines.size(); i != e; ++i) {
1294  Annotator.calculateFormattingInformation(*AnnotatedLines[i]);
1295  }
1296  Annotator.setCommentLineLevels(AnnotatedLines);
1297 
1298  WhitespaceManager Whitespaces(
1299  Env.getSourceManager(), Style,
1300  inputUsesCRLF(Env.getSourceManager().getBufferData(Env.getFileID())));
1301  ContinuationIndenter Indenter(Style, Tokens.getKeywords(),
1302  Env.getSourceManager(), Whitespaces, Encoding,
1303  BinPackInconclusiveFunctions);
1304  unsigned Penalty =
1305  UnwrappedLineFormatter(&Indenter, &Whitespaces, Style,
1306  Tokens.getKeywords(), Env.getSourceManager(),
1307  Status)
1308  .format(AnnotatedLines, /*DryRun=*/false,
1309  /*AdditionalIndent=*/0,
1310  /*FixBadIndentation=*/false,
1311  /*FirstStartColumn=*/Env.getFirstStartColumn(),
1312  /*NextStartColumn=*/Env.getNextStartColumn(),
1313  /*LastStartColumn=*/Env.getLastStartColumn());
1314  for (const auto &R : Whitespaces.generateReplacements())
1315  if (Result.add(R))
1316  return std::make_pair(Result, 0);
1317  return std::make_pair(Result, Penalty);
1318  }
1319 
1320 private:
1321  static bool inputUsesCRLF(StringRef Text) {
1322  return Text.count('\r') * 2 > Text.count('\n');
1323  }
1324 
1325  bool
1326  hasCpp03IncompatibleFormat(const SmallVectorImpl<AnnotatedLine *> &Lines) {
1327  for (const AnnotatedLine *Line : Lines) {
1328  if (hasCpp03IncompatibleFormat(Line->Children))
1329  return true;
1330  for (FormatToken *Tok = Line->First->Next; Tok; Tok = Tok->Next) {
1332  if (Tok->is(tok::coloncolon) && Tok->Previous->is(TT_TemplateOpener))
1333  return true;
1334  if (Tok->is(TT_TemplateCloser) &&
1335  Tok->Previous->is(TT_TemplateCloser))
1336  return true;
1337  }
1338  }
1339  }
1340  return false;
1341  }
1342 
1343  int countVariableAlignments(const SmallVectorImpl<AnnotatedLine *> &Lines) {
1344  int AlignmentDiff = 0;
1345  for (const AnnotatedLine *Line : Lines) {
1346  AlignmentDiff += countVariableAlignments(Line->Children);
1347  for (FormatToken *Tok = Line->First; Tok && Tok->Next; Tok = Tok->Next) {
1348  if (!Tok->is(TT_PointerOrReference))
1349  continue;
1350  bool SpaceBefore =
1352  bool SpaceAfter = Tok->Next->WhitespaceRange.getBegin() !=
1354  if (SpaceBefore && !SpaceAfter)
1355  ++AlignmentDiff;
1356  if (!SpaceBefore && SpaceAfter)
1357  --AlignmentDiff;
1358  }
1359  }
1360  return AlignmentDiff;
1361  }
1362 
1363  void
1364  deriveLocalStyle(const SmallVectorImpl<AnnotatedLine *> &AnnotatedLines) {
1365  bool HasBinPackedFunction = false;
1366  bool HasOnePerLineFunction = false;
1367  for (unsigned i = 0, e = AnnotatedLines.size(); i != e; ++i) {
1368  if (!AnnotatedLines[i]->First->Next)
1369  continue;
1370  FormatToken *Tok = AnnotatedLines[i]->First->Next;
1371  while (Tok->Next) {
1372  if (Tok->PackingKind == PPK_BinPacked)
1373  HasBinPackedFunction = true;
1374  if (Tok->PackingKind == PPK_OnePerLine)
1375  HasOnePerLineFunction = true;
1376 
1377  Tok = Tok->Next;
1378  }
1379  }
1380  if (Style.DerivePointerAlignment)
1381  Style.PointerAlignment = countVariableAlignments(AnnotatedLines) <= 0
1382  ? FormatStyle::PAS_Left
1383  : FormatStyle::PAS_Right;
1384  if (Style.Standard == FormatStyle::LS_Auto)
1385  Style.Standard = hasCpp03IncompatibleFormat(AnnotatedLines)
1386  ? FormatStyle::LS_Cpp11
1387  : FormatStyle::LS_Cpp03;
1388  BinPackInconclusiveFunctions =
1389  HasBinPackedFunction || !HasOnePerLineFunction;
1390  }
1391 
1392  bool BinPackInconclusiveFunctions;
1393  FormattingAttemptStatus *Status;
1394 };
1395 
1396 // This class clean up the erroneous/redundant code around the given ranges in
1397 // file.
1398 class Cleaner : public TokenAnalyzer {
1399 public:
1400  Cleaner(const Environment &Env, const FormatStyle &Style)
1401  : TokenAnalyzer(Env, Style),
1402  DeletedTokens(FormatTokenLess(Env.getSourceManager())) {}
1403 
1404  // FIXME: eliminate unused parameters.
1405  std::pair<tooling::Replacements, unsigned>
1406  analyze(TokenAnnotator &Annotator,
1407  SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1408  FormatTokenLexer &Tokens) override {
1409  // FIXME: in the current implementation the granularity of affected range
1410  // is an annotated line. However, this is not sufficient. Furthermore,
1411  // redundant code introduced by replacements does not necessarily
1412  // intercept with ranges of replacements that result in the redundancy.
1413  // To determine if some redundant code is actually introduced by
1414  // replacements(e.g. deletions), we need to come up with a more
1415  // sophisticated way of computing affected ranges.
1416  AffectedRangeMgr.computeAffectedLines(AnnotatedLines);
1417 
1418  checkEmptyNamespace(AnnotatedLines);
1419 
1420  for (auto &Line : AnnotatedLines) {
1421  if (Line->Affected) {
1422  cleanupRight(Line->First, tok::comma, tok::comma);
1423  cleanupRight(Line->First, TT_CtorInitializerColon, tok::comma);
1424  cleanupRight(Line->First, tok::l_paren, tok::comma);
1425  cleanupLeft(Line->First, tok::comma, tok::r_paren);
1426  cleanupLeft(Line->First, TT_CtorInitializerComma, tok::l_brace);
1427  cleanupLeft(Line->First, TT_CtorInitializerColon, tok::l_brace);
1428  cleanupLeft(Line->First, TT_CtorInitializerColon, tok::equal);
1429  }
1430  }
1431 
1432  return {generateFixes(), 0};
1433  }
1434 
1435 private:
1436  bool containsOnlyComments(const AnnotatedLine &Line) {
1437  for (FormatToken *Tok = Line.First; Tok != nullptr; Tok = Tok->Next) {
1438  if (Tok->isNot(tok::comment))
1439  return false;
1440  }
1441  return true;
1442  }
1443 
1444  // Iterate through all lines and remove any empty (nested) namespaces.
1445  void checkEmptyNamespace(SmallVectorImpl<AnnotatedLine *> &AnnotatedLines) {
1446  std::set<unsigned> DeletedLines;
1447  for (unsigned i = 0, e = AnnotatedLines.size(); i != e; ++i) {
1448  auto &Line = *AnnotatedLines[i];
1449  if (Line.startsWithNamespace()) {
1450  checkEmptyNamespace(AnnotatedLines, i, i, DeletedLines);
1451  }
1452  }
1453 
1454  for (auto Line : DeletedLines) {
1455  FormatToken *Tok = AnnotatedLines[Line]->First;
1456  while (Tok) {
1457  deleteToken(Tok);
1458  Tok = Tok->Next;
1459  }
1460  }
1461  }
1462 
1463  // The function checks if the namespace, which starts from \p CurrentLine, and
1464  // its nested namespaces are empty and delete them if they are empty. It also
1465  // sets \p NewLine to the last line checked.
1466  // Returns true if the current namespace is empty.
1467  bool checkEmptyNamespace(SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1468  unsigned CurrentLine, unsigned &NewLine,
1469  std::set<unsigned> &DeletedLines) {
1470  unsigned InitLine = CurrentLine, End = AnnotatedLines.size();
1471  if (Style.BraceWrapping.AfterNamespace) {
1472  // If the left brace is in a new line, we should consume it first so that
1473  // it does not make the namespace non-empty.
1474  // FIXME: error handling if there is no left brace.
1475  if (!AnnotatedLines[++CurrentLine]->startsWith(tok::l_brace)) {
1476  NewLine = CurrentLine;
1477  return false;
1478  }
1479  } else if (!AnnotatedLines[CurrentLine]->endsWith(tok::l_brace)) {
1480  return false;
1481  }
1482  while (++CurrentLine < End) {
1483  if (AnnotatedLines[CurrentLine]->startsWith(tok::r_brace))
1484  break;
1485 
1486  if (AnnotatedLines[CurrentLine]->startsWithNamespace()) {
1487  if (!checkEmptyNamespace(AnnotatedLines, CurrentLine, NewLine,
1488  DeletedLines))
1489  return false;
1490  CurrentLine = NewLine;
1491  continue;
1492  }
1493 
1494  if (containsOnlyComments(*AnnotatedLines[CurrentLine]))
1495  continue;
1496 
1497  // If there is anything other than comments or nested namespaces in the
1498  // current namespace, the namespace cannot be empty.
1499  NewLine = CurrentLine;
1500  return false;
1501  }
1502 
1503  NewLine = CurrentLine;
1504  if (CurrentLine >= End)
1505  return false;
1506 
1507  // Check if the empty namespace is actually affected by changed ranges.
1508  if (!AffectedRangeMgr.affectsCharSourceRange(CharSourceRange::getCharRange(
1509  AnnotatedLines[InitLine]->First->Tok.getLocation(),
1510  AnnotatedLines[CurrentLine]->Last->Tok.getEndLoc())))
1511  return false;
1512 
1513  for (unsigned i = InitLine; i <= CurrentLine; ++i) {
1514  DeletedLines.insert(i);
1515  }
1516 
1517  return true;
1518  }
1519 
1520  // Checks pairs {start, start->next},..., {end->previous, end} and deletes one
1521  // of the token in the pair if the left token has \p LK token kind and the
1522  // right token has \p RK token kind. If \p DeleteLeft is true, the left token
1523  // is deleted on match; otherwise, the right token is deleted.
1524  template <typename LeftKind, typename RightKind>
1525  void cleanupPair(FormatToken *Start, LeftKind LK, RightKind RK,
1526  bool DeleteLeft) {
1527  auto NextNotDeleted = [this](const FormatToken &Tok) -> FormatToken * {
1528  for (auto *Res = Tok.Next; Res; Res = Res->Next)
1529  if (!Res->is(tok::comment) &&
1530  DeletedTokens.find(Res) == DeletedTokens.end())
1531  return Res;
1532  return nullptr;
1533  };
1534  for (auto *Left = Start; Left;) {
1535  auto *Right = NextNotDeleted(*Left);
1536  if (!Right)
1537  break;
1538  if (Left->is(LK) && Right->is(RK)) {
1539  deleteToken(DeleteLeft ? Left : Right);
1540  for (auto *Tok = Left->Next; Tok && Tok != Right; Tok = Tok->Next)
1541  deleteToken(Tok);
1542  // If the right token is deleted, we should keep the left token
1543  // unchanged and pair it with the new right token.
1544  if (!DeleteLeft)
1545  continue;
1546  }
1547  Left = Right;
1548  }
1549  }
1550 
1551  template <typename LeftKind, typename RightKind>
1552  void cleanupLeft(FormatToken *Start, LeftKind LK, RightKind RK) {
1553  cleanupPair(Start, LK, RK, /*DeleteLeft=*/true);
1554  }
1555 
1556  template <typename LeftKind, typename RightKind>
1557  void cleanupRight(FormatToken *Start, LeftKind LK, RightKind RK) {
1558  cleanupPair(Start, LK, RK, /*DeleteLeft=*/false);
1559  }
1560 
1561  // Delete the given token.
1562  inline void deleteToken(FormatToken *Tok) {
1563  if (Tok)
1564  DeletedTokens.insert(Tok);
1565  }
1566 
1567  tooling::Replacements generateFixes() {
1568  tooling::Replacements Fixes;
1569  std::vector<FormatToken *> Tokens;
1570  std::copy(DeletedTokens.begin(), DeletedTokens.end(),
1571  std::back_inserter(Tokens));
1572 
1573  // Merge multiple continuous token deletions into one big deletion so that
1574  // the number of replacements can be reduced. This makes computing affected
1575  // ranges more efficient when we run reformat on the changed code.
1576  unsigned Idx = 0;
1577  while (Idx < Tokens.size()) {
1578  unsigned St = Idx, End = Idx;
1579  while ((End + 1) < Tokens.size() &&
1580  Tokens[End]->Next == Tokens[End + 1]) {
1581  End++;
1582  }
1583  auto SR = CharSourceRange::getCharRange(Tokens[St]->Tok.getLocation(),
1584  Tokens[End]->Tok.getEndLoc());
1585  auto Err =
1586  Fixes.add(tooling::Replacement(Env.getSourceManager(), SR, ""));
1587  // FIXME: better error handling. for now just print error message and skip
1588  // for the release version.
1589  if (Err) {
1590  llvm::errs() << llvm::toString(std::move(Err)) << "\n";
1591  assert(false && "Fixes must not conflict!");
1592  }
1593  Idx = End + 1;
1594  }
1595 
1596  return Fixes;
1597  }
1598 
1599  // Class for less-than inequality comparason for the set `RedundantTokens`.
1600  // We store tokens in the order they appear in the translation unit so that
1601  // we do not need to sort them in `generateFixes()`.
1602  struct FormatTokenLess {
1603  FormatTokenLess(const SourceManager &SM) : SM(SM) {}
1604 
1605  bool operator()(const FormatToken *LHS, const FormatToken *RHS) const {
1606  return SM.isBeforeInTranslationUnit(LHS->Tok.getLocation(),
1607  RHS->Tok.getLocation());
1608  }
1609  const SourceManager &SM;
1610  };
1611 
1612  // Tokens to be deleted.
1613  std::set<FormatToken *, FormatTokenLess> DeletedTokens;
1614 };
1615 
1616 class ObjCHeaderStyleGuesser : public TokenAnalyzer {
1617 public:
1618  ObjCHeaderStyleGuesser(const Environment &Env, const FormatStyle &Style)
1619  : TokenAnalyzer(Env, Style), IsObjC(false) {}
1620 
1621  std::pair<tooling::Replacements, unsigned>
1622  analyze(TokenAnnotator &Annotator,
1623  SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1624  FormatTokenLexer &Tokens) override {
1625  assert(Style.Language == FormatStyle::LK_Cpp);
1626  IsObjC = guessIsObjC(Env.getSourceManager(), AnnotatedLines,
1627  Tokens.getKeywords());
1628  tooling::Replacements Result;
1629  return {Result, 0};
1630  }
1631 
1632  bool isObjC() { return IsObjC; }
1633 
1634 private:
1635  static bool
1636  guessIsObjC(const SourceManager &SourceManager,
1637  const SmallVectorImpl<AnnotatedLine *> &AnnotatedLines,
1638  const AdditionalKeywords &Keywords) {
1639  // Keep this array sorted, since we are binary searching over it.
1640  static constexpr llvm::StringLiteral FoundationIdentifiers[] = {
1641  "CGFloat",
1642  "CGPoint",
1643  "CGPointMake",
1644  "CGPointZero",
1645  "CGRect",
1646  "CGRectEdge",
1647  "CGRectInfinite",
1648  "CGRectMake",
1649  "CGRectNull",
1650  "CGRectZero",
1651  "CGSize",
1652  "CGSizeMake",
1653  "CGVector",
1654  "CGVectorMake",
1655  "NSAffineTransform",
1656  "NSArray",
1657  "NSAttributedString",
1658  "NSBlockOperation",
1659  "NSBundle",
1660  "NSCache",
1661  "NSCalendar",
1662  "NSCharacterSet",
1663  "NSCountedSet",
1664  "NSData",
1665  "NSDataDetector",
1666  "NSDecimal",
1667  "NSDecimalNumber",
1668  "NSDictionary",
1669  "NSEdgeInsets",
1670  "NSHashTable",
1671  "NSIndexPath",
1672  "NSIndexSet",
1673  "NSInteger",
1674  "NSInvocationOperation",
1675  "NSLocale",
1676  "NSMapTable",
1677  "NSMutableArray",
1678  "NSMutableAttributedString",
1679  "NSMutableCharacterSet",
1680  "NSMutableData",
1681  "NSMutableDictionary",
1682  "NSMutableIndexSet",
1683  "NSMutableOrderedSet",
1684  "NSMutableSet",
1685  "NSMutableString",
1686  "NSNumber",
1687  "NSNumberFormatter",
1688  "NSObject",
1689  "NSOperation",
1690  "NSOperationQueue",
1691  "NSOperationQueuePriority",
1692  "NSOrderedSet",
1693  "NSPoint",
1694  "NSPointerArray",
1695  "NSQualityOfService",
1696  "NSRange",
1697  "NSRect",
1698  "NSRegularExpression",
1699  "NSSet",
1700  "NSSize",
1701  "NSString",
1702  "NSTimeZone",
1703  "NSUInteger",
1704  "NSURL",
1705  "NSURLComponents",
1706  "NSURLQueryItem",
1707  "NSUUID",
1708  "NSValue",
1709  "UIImage",
1710  "UIView",
1711  };
1712 
1713  for (auto Line : AnnotatedLines) {
1714  for (const FormatToken *FormatTok = Line->First; FormatTok;
1715  FormatTok = FormatTok->Next) {
1716  if ((FormatTok->Previous && FormatTok->Previous->is(tok::at) &&
1717  (FormatTok->Tok.getObjCKeywordID() != tok::objc_not_keyword ||
1718  FormatTok->isOneOf(tok::numeric_constant, tok::l_square,
1719  tok::l_brace))) ||
1720  (FormatTok->Tok.isAnyIdentifier() &&
1721  std::binary_search(std::begin(FoundationIdentifiers),
1722  std::end(FoundationIdentifiers),
1723  FormatTok->TokenText)) ||
1724  FormatTok->is(TT_ObjCStringLiteral) ||
1725  FormatTok->isOneOf(Keywords.kw_NS_CLOSED_ENUM, Keywords.kw_NS_ENUM,
1726  Keywords.kw_NS_OPTIONS, TT_ObjCBlockLBrace,
1727  TT_ObjCBlockLParen, TT_ObjCDecl, TT_ObjCForIn,
1728  TT_ObjCMethodExpr, TT_ObjCMethodSpecifier,
1729  TT_ObjCProperty)) {
1730  LLVM_DEBUG(llvm::dbgs()
1731  << "Detected ObjC at location "
1732  << FormatTok->Tok.getLocation().printToString(
1733  SourceManager)
1734  << " token: " << FormatTok->TokenText << " token type: "
1735  << getTokenTypeName(FormatTok->Type) << "\n");
1736  return true;
1737  }
1738  if (guessIsObjC(SourceManager, Line->Children, Keywords))
1739  return true;
1740  }
1741  }
1742  return false;
1743  }
1744 
1745  bool IsObjC;
1746 };
1747 
1748 struct IncludeDirective {
1749  StringRef Filename;
1750  StringRef Text;
1751  unsigned Offset;
1753 };
1754 
1755 struct JavaImportDirective {
1756  StringRef Identifier;
1757  StringRef Text;
1758  unsigned Offset;
1759  std::vector<StringRef> AssociatedCommentLines;
1760  bool IsStatic;
1761 };
1762 
1763 } // end anonymous namespace
1764 
1765 // Determines whether 'Ranges' intersects with ('Start', 'End').
1766 static bool affectsRange(ArrayRef<tooling::Range> Ranges, unsigned Start,
1767  unsigned End) {
1768  for (auto Range : Ranges) {
1769  if (Range.getOffset() < End &&
1770  Range.getOffset() + Range.getLength() > Start)
1771  return true;
1772  }
1773  return false;
1774 }
1775 
1776 // Returns a pair (Index, OffsetToEOL) describing the position of the cursor
1777 // before sorting/deduplicating. Index is the index of the include under the
1778 // cursor in the original set of includes. If this include has duplicates, it is
1779 // the index of the first of the duplicates as the others are going to be
1780 // removed. OffsetToEOL describes the cursor's position relative to the end of
1781 // its current line.
1782 // If `Cursor` is not on any #include, `Index` will be UINT_MAX.
1783 static std::pair<unsigned, unsigned>
1785  const SmallVectorImpl<unsigned> &Indices, unsigned Cursor) {
1786  unsigned CursorIndex = UINT_MAX;
1787  unsigned OffsetToEOL = 0;
1788  for (int i = 0, e = Includes.size(); i != e; ++i) {
1789  unsigned Start = Includes[Indices[i]].Offset;
1790  unsigned End = Start + Includes[Indices[i]].Text.size();
1791  if (!(Cursor >= Start && Cursor < End))
1792  continue;
1793  CursorIndex = Indices[i];
1794  OffsetToEOL = End - Cursor;
1795  // Put the cursor on the only remaining #include among the duplicate
1796  // #includes.
1797  while (--i >= 0 && Includes[CursorIndex].Text == Includes[Indices[i]].Text)
1798  CursorIndex = i;
1799  break;
1800  }
1801  return std::make_pair(CursorIndex, OffsetToEOL);
1802 }
1803 
1804 // Sorts and deduplicate a block of includes given by 'Includes' alphabetically
1805 // adding the necessary replacement to 'Replaces'. 'Includes' must be in strict
1806 // source order.
1807 // #include directives with the same text will be deduplicated, and only the
1808 // first #include in the duplicate #includes remains. If the `Cursor` is
1809 // provided and put on a deleted #include, it will be moved to the remaining
1810 // #include in the duplicate #includes.
1811 static void sortCppIncludes(const FormatStyle &Style,
1812  const SmallVectorImpl<IncludeDirective> &Includes,
1813  ArrayRef<tooling::Range> Ranges, StringRef FileName,
1814  StringRef Code, tooling::Replacements &Replaces,
1815  unsigned *Cursor) {
1816  unsigned IncludesBeginOffset = Includes.front().Offset;
1817  unsigned IncludesEndOffset =
1818  Includes.back().Offset + Includes.back().Text.size();
1819  unsigned IncludesBlockSize = IncludesEndOffset - IncludesBeginOffset;
1820  if (!affectsRange(Ranges, IncludesBeginOffset, IncludesEndOffset))
1821  return;
1822  SmallVector<unsigned, 16> Indices;
1823  for (unsigned i = 0, e = Includes.size(); i != e; ++i)
1824  Indices.push_back(i);
1825  llvm::stable_sort(Indices, [&](unsigned LHSI, unsigned RHSI) {
1826  return std::tie(Includes[LHSI].Category, Includes[LHSI].Filename) <
1827  std::tie(Includes[RHSI].Category, Includes[RHSI].Filename);
1828  });
1829  // The index of the include on which the cursor will be put after
1830  // sorting/deduplicating.
1831  unsigned CursorIndex;
1832  // The offset from cursor to the end of line.
1833  unsigned CursorToEOLOffset;
1834  if (Cursor)
1835  std::tie(CursorIndex, CursorToEOLOffset) =
1836  FindCursorIndex(Includes, Indices, *Cursor);
1837 
1838  // Deduplicate #includes.
1839  Indices.erase(std::unique(Indices.begin(), Indices.end(),
1840  [&](unsigned LHSI, unsigned RHSI) {
1841  return Includes[LHSI].Text == Includes[RHSI].Text;
1842  }),
1843  Indices.end());
1844 
1845  int CurrentCategory = Includes.front().Category;
1846 
1847  // If the #includes are out of order, we generate a single replacement fixing
1848  // the entire block. Otherwise, no replacement is generated.
1849  // In case Style.IncldueStyle.IncludeBlocks != IBS_Preserve, this check is not
1850  // enough as additional newlines might be added or removed across #include
1851  // blocks. This we handle below by generating the updated #imclude blocks and
1852  // comparing it to the original.
1853  if (Indices.size() == Includes.size() &&
1854  std::is_sorted(Indices.begin(), Indices.end()) &&
1855  Style.IncludeStyle.IncludeBlocks == tooling::IncludeStyle::IBS_Preserve)
1856  return;
1857 
1858  std::string result;
1859  for (unsigned Index : Indices) {
1860  if (!result.empty()) {
1861  result += "\n";
1862  if (Style.IncludeStyle.IncludeBlocks ==
1863  tooling::IncludeStyle::IBS_Regroup &&
1864  CurrentCategory != Includes[Index].Category)
1865  result += "\n";
1866  }
1867  result += Includes[Index].Text;
1868  if (Cursor && CursorIndex == Index)
1869  *Cursor = IncludesBeginOffset + result.size() - CursorToEOLOffset;
1870  CurrentCategory = Includes[Index].Category;
1871  }
1872 
1873  // If the #includes are out of order, we generate a single replacement fixing
1874  // the entire range of blocks. Otherwise, no replacement is generated.
1875  if (result == Code.substr(IncludesBeginOffset, IncludesBlockSize))
1876  return;
1877 
1878  auto Err = Replaces.add(tooling::Replacement(
1879  FileName, Includes.front().Offset, IncludesBlockSize, result));
1880  // FIXME: better error handling. For now, just skip the replacement for the
1881  // release version.
1882  if (Err) {
1883  llvm::errs() << llvm::toString(std::move(Err)) << "\n";
1884  assert(false);
1885  }
1886 }
1887 
1888 namespace {
1889 
1890 const char CppIncludeRegexPattern[] =
1891  R"(^[\t\ ]*#[\t\ ]*(import|include)[^"<]*(["<][^">]*[">]))";
1892 
1893 } // anonymous namespace
1894 
1896  ArrayRef<tooling::Range> Ranges,
1897  StringRef FileName,
1898  tooling::Replacements &Replaces,
1899  unsigned *Cursor) {
1900  unsigned Prev = 0;
1901  unsigned SearchFrom = 0;
1902  llvm::Regex IncludeRegex(CppIncludeRegexPattern);
1903  SmallVector<StringRef, 4> Matches;
1904  SmallVector<IncludeDirective, 16> IncludesInBlock;
1905 
1906  // In compiled files, consider the first #include to be the main #include of
1907  // the file if it is not a system #include. This ensures that the header
1908  // doesn't have hidden dependencies
1909  // (http://llvm.org/docs/CodingStandards.html#include-style).
1910  //
1911  // FIXME: Do some sanity checking, e.g. edit distance of the base name, to fix
1912  // cases where the first #include is unlikely to be the main header.
1913  tooling::IncludeCategoryManager Categories(Style.IncludeStyle, FileName);
1914  bool FirstIncludeBlock = true;
1915  bool MainIncludeFound = false;
1916  bool FormattingOff = false;
1917 
1918  for (;;) {
1919  auto Pos = Code.find('\n', SearchFrom);
1920  StringRef Line =
1921  Code.substr(Prev, (Pos != StringRef::npos ? Pos : Code.size()) - Prev);
1922 
1923  StringRef Trimmed = Line.trim();
1924  if (Trimmed == "// clang-format off" || Trimmed == "/* clang-format off */")
1925  FormattingOff = true;
1926  else if (Trimmed == "// clang-format on" ||
1927  Trimmed == "/* clang-format on */")
1928  FormattingOff = false;
1929 
1930  const bool EmptyLineSkipped =
1931  Trimmed.empty() &&
1932  (Style.IncludeStyle.IncludeBlocks == tooling::IncludeStyle::IBS_Merge ||
1933  Style.IncludeStyle.IncludeBlocks ==
1934  tooling::IncludeStyle::IBS_Regroup);
1935 
1936  if (!FormattingOff && !Line.endswith("\\")) {
1937  if (IncludeRegex.match(Line, &Matches)) {
1938  StringRef IncludeName = Matches[2];
1939  int Category = Categories.getIncludePriority(
1940  IncludeName,
1941  /*CheckMainHeader=*/!MainIncludeFound && FirstIncludeBlock);
1942  if (Category == 0)
1943  MainIncludeFound = true;
1944  IncludesInBlock.push_back({IncludeName, Line, Prev, Category});
1945  } else if (!IncludesInBlock.empty() && !EmptyLineSkipped) {
1946  sortCppIncludes(Style, IncludesInBlock, Ranges, FileName, Code,
1947  Replaces, Cursor);
1948  IncludesInBlock.clear();
1949  FirstIncludeBlock = false;
1950  }
1951  Prev = Pos + 1;
1952  }
1953  if (Pos == StringRef::npos || Pos + 1 == Code.size())
1954  break;
1955  SearchFrom = Pos + 1;
1956  }
1957  if (!IncludesInBlock.empty()) {
1958  sortCppIncludes(Style, IncludesInBlock, Ranges, FileName, Code, Replaces,
1959  Cursor);
1960  }
1961  return Replaces;
1962 }
1963 
1964 // Returns group number to use as a first order sort on imports. Gives UINT_MAX
1965 // if the import does not match any given groups.
1966 static unsigned findJavaImportGroup(const FormatStyle &Style,
1967  StringRef ImportIdentifier) {
1968  unsigned LongestMatchIndex = UINT_MAX;
1969  unsigned LongestMatchLength = 0;
1970  for (unsigned I = 0; I < Style.JavaImportGroups.size(); I++) {
1971  std::string GroupPrefix = Style.JavaImportGroups[I];
1972  if (ImportIdentifier.startswith(GroupPrefix) &&
1973  GroupPrefix.length() > LongestMatchLength) {
1974  LongestMatchIndex = I;
1975  LongestMatchLength = GroupPrefix.length();
1976  }
1977  }
1978  return LongestMatchIndex;
1979 }
1980 
1981 // Sorts and deduplicates a block of includes given by 'Imports' based on
1982 // JavaImportGroups, then adding the necessary replacement to 'Replaces'.
1983 // Import declarations with the same text will be deduplicated. Between each
1984 // import group, a newline is inserted, and within each import group, a
1985 // lexicographic sort based on ASCII value is performed.
1986 static void sortJavaImports(const FormatStyle &Style,
1987  const SmallVectorImpl<JavaImportDirective> &Imports,
1988  ArrayRef<tooling::Range> Ranges, StringRef FileName,
1989  StringRef Code, tooling::Replacements &Replaces) {
1990  unsigned ImportsBeginOffset = Imports.front().Offset;
1991  unsigned ImportsEndOffset =
1992  Imports.back().Offset + Imports.back().Text.size();
1993  unsigned ImportsBlockSize = ImportsEndOffset - ImportsBeginOffset;
1994  if (!affectsRange(Ranges, ImportsBeginOffset, ImportsEndOffset))
1995  return;
1996  SmallVector<unsigned, 16> Indices;
1997  SmallVector<unsigned, 16> JavaImportGroups;
1998  for (unsigned i = 0, e = Imports.size(); i != e; ++i) {
1999  Indices.push_back(i);
2000  JavaImportGroups.push_back(
2001  findJavaImportGroup(Style, Imports[i].Identifier));
2002  }
2003  llvm::sort(Indices, [&](unsigned LHSI, unsigned RHSI) {
2004  // Negating IsStatic to push static imports above non-static imports.
2005  return std::make_tuple(!Imports[LHSI].IsStatic, JavaImportGroups[LHSI],
2006  Imports[LHSI].Identifier) <
2007  std::make_tuple(!Imports[RHSI].IsStatic, JavaImportGroups[RHSI],
2008  Imports[RHSI].Identifier);
2009  });
2010 
2011  // Deduplicate imports.
2012  Indices.erase(std::unique(Indices.begin(), Indices.end(),
2013  [&](unsigned LHSI, unsigned RHSI) {
2014  return Imports[LHSI].Text == Imports[RHSI].Text;
2015  }),
2016  Indices.end());
2017 
2018  bool CurrentIsStatic = Imports[Indices.front()].IsStatic;
2019  unsigned CurrentImportGroup = JavaImportGroups[Indices.front()];
2020 
2021  std::string result;
2022  for (unsigned Index : Indices) {
2023  if (!result.empty()) {
2024  result += "\n";
2025  if (CurrentIsStatic != Imports[Index].IsStatic ||
2026  CurrentImportGroup != JavaImportGroups[Index])
2027  result += "\n";
2028  }
2029  for (StringRef CommentLine : Imports[Index].AssociatedCommentLines) {
2030  result += CommentLine;
2031  result += "\n";
2032  }
2033  result += Imports[Index].Text;
2034  CurrentIsStatic = Imports[Index].IsStatic;
2035  CurrentImportGroup = JavaImportGroups[Index];
2036  }
2037 
2038  // If the imports are out of order, we generate a single replacement fixing
2039  // the entire block. Otherwise, no replacement is generated.
2040  if (result == Code.substr(Imports.front().Offset, ImportsBlockSize))
2041  return;
2042 
2043  auto Err = Replaces.add(tooling::Replacement(FileName, Imports.front().Offset,
2044  ImportsBlockSize, result));
2045  // FIXME: better error handling. For now, just skip the replacement for the
2046  // release version.
2047  if (Err) {
2048  llvm::errs() << llvm::toString(std::move(Err)) << "\n";
2049  assert(false);
2050  }
2051 }
2052 
2053 namespace {
2054 
2055 const char JavaImportRegexPattern[] =
2056  "^[\t ]*import[\t ]+(static[\t ]*)?([^\t ]*)[\t ]*;";
2057 
2058 } // anonymous namespace
2059 
2061  ArrayRef<tooling::Range> Ranges,
2062  StringRef FileName,
2063  tooling::Replacements &Replaces) {
2064  unsigned Prev = 0;
2065  unsigned SearchFrom = 0;
2066  llvm::Regex ImportRegex(JavaImportRegexPattern);
2067  SmallVector<StringRef, 4> Matches;
2068  SmallVector<JavaImportDirective, 16> ImportsInBlock;
2069  std::vector<StringRef> AssociatedCommentLines;
2070 
2071  bool FormattingOff = false;
2072 
2073  for (;;) {
2074  auto Pos = Code.find('\n', SearchFrom);
2075  StringRef Line =
2076  Code.substr(Prev, (Pos != StringRef::npos ? Pos : Code.size()) - Prev);
2077 
2078  StringRef Trimmed = Line.trim();
2079  if (Trimmed == "// clang-format off")
2080  FormattingOff = true;
2081  else if (Trimmed == "// clang-format on")
2082  FormattingOff = false;
2083 
2084  if (ImportRegex.match(Line, &Matches)) {
2085  if (FormattingOff) {
2086  // If at least one import line has formatting turned off, turn off
2087  // formatting entirely.
2088  return Replaces;
2089  }
2090  StringRef Static = Matches[1];
2091  StringRef Identifier = Matches[2];
2092  bool IsStatic = false;
2093  if (Static.contains("static")) {
2094  IsStatic = true;
2095  }
2096  ImportsInBlock.push_back(
2097  {Identifier, Line, Prev, AssociatedCommentLines, IsStatic});
2098  AssociatedCommentLines.clear();
2099  } else if (Trimmed.size() > 0 && !ImportsInBlock.empty()) {
2100  // Associating comments within the imports with the nearest import below
2101  AssociatedCommentLines.push_back(Line);
2102  }
2103  Prev = Pos + 1;
2104  if (Pos == StringRef::npos || Pos + 1 == Code.size())
2105  break;
2106  SearchFrom = Pos + 1;
2107  }
2108  if (!ImportsInBlock.empty())
2109  sortJavaImports(Style, ImportsInBlock, Ranges, FileName, Code, Replaces);
2110  return Replaces;
2111 }
2112 
2113 bool isMpegTS(StringRef Code) {
2114  // MPEG transport streams use the ".ts" file extension. clang-format should
2115  // not attempt to format those. MPEG TS' frame format starts with 0x47 every
2116  // 189 bytes - detect that and return.
2117  return Code.size() > 188 && Code[0] == 0x47 && Code[188] == 0x47;
2118 }
2119 
2120 bool isLikelyXml(StringRef Code) { return Code.ltrim().startswith("<"); }
2121 
2122 tooling::Replacements sortIncludes(const FormatStyle &Style, StringRef Code,
2123  ArrayRef<tooling::Range> Ranges,
2124  StringRef FileName, unsigned *Cursor) {
2125  tooling::Replacements Replaces;
2126  if (!Style.SortIncludes)
2127  return Replaces;
2128  if (isLikelyXml(Code))
2129  return Replaces;
2130  if (Style.Language == FormatStyle::LanguageKind::LK_JavaScript &&
2131  isMpegTS(Code))
2132  return Replaces;
2133  if (Style.Language == FormatStyle::LanguageKind::LK_JavaScript)
2134  return sortJavaScriptImports(Style, Code, Ranges, FileName);
2135  if (Style.Language == FormatStyle::LanguageKind::LK_Java)
2136  return sortJavaImports(Style, Code, Ranges, FileName, Replaces);
2137  sortCppIncludes(Style, Code, Ranges, FileName, Replaces, Cursor);
2138  return Replaces;
2139 }
2140 
2141 template <typename T>
2143 processReplacements(T ProcessFunc, StringRef Code,
2144  const tooling::Replacements &Replaces,
2145  const FormatStyle &Style) {
2146  if (Replaces.empty())
2147  return tooling::Replacements();
2148 
2149  auto NewCode = applyAllReplacements(Code, Replaces);
2150  if (!NewCode)
2151  return NewCode.takeError();
2152  std::vector<tooling::Range> ChangedRanges = Replaces.getAffectedRanges();
2153  StringRef FileName = Replaces.begin()->getFilePath();
2154 
2155  tooling::Replacements FormatReplaces =
2156  ProcessFunc(Style, *NewCode, ChangedRanges, FileName);
2157 
2158  return Replaces.merge(FormatReplaces);
2159 }
2160 
2162 formatReplacements(StringRef Code, const tooling::Replacements &Replaces,
2163  const FormatStyle &Style) {
2164  // We need to use lambda function here since there are two versions of
2165  // `sortIncludes`.
2166  auto SortIncludes = [](const FormatStyle &Style, StringRef Code,
2167  std::vector<tooling::Range> Ranges,
2168  StringRef FileName) -> tooling::Replacements {
2169  return sortIncludes(Style, Code, Ranges, FileName);
2170  };
2171  auto SortedReplaces =
2172  processReplacements(SortIncludes, Code, Replaces, Style);
2173  if (!SortedReplaces)
2174  return SortedReplaces.takeError();
2175 
2176  // We need to use lambda function here since there are two versions of
2177  // `reformat`.
2178  auto Reformat = [](const FormatStyle &Style, StringRef Code,
2179  std::vector<tooling::Range> Ranges,
2180  StringRef FileName) -> tooling::Replacements {
2181  return reformat(Style, Code, Ranges, FileName);
2182  };
2183  return processReplacements(Reformat, Code, *SortedReplaces, Style);
2184 }
2185 
2186 namespace {
2187 
2188 inline bool isHeaderInsertion(const tooling::Replacement &Replace) {
2189  return Replace.getOffset() == UINT_MAX && Replace.getLength() == 0 &&
2190  llvm::Regex(CppIncludeRegexPattern)
2191  .match(Replace.getReplacementText());
2192 }
2193 
2194 inline bool isHeaderDeletion(const tooling::Replacement &Replace) {
2195  return Replace.getOffset() == UINT_MAX && Replace.getLength() == 1;
2196 }
2197 
2198 // FIXME: insert empty lines between newly created blocks.
2200 fixCppIncludeInsertions(StringRef Code, const tooling::Replacements &Replaces,
2201  const FormatStyle &Style) {
2202  if (!Style.isCpp())
2203  return Replaces;
2204 
2205  tooling::Replacements HeaderInsertions;
2206  std::set<llvm::StringRef> HeadersToDelete;
2207  tooling::Replacements Result;
2208  for (const auto &R : Replaces) {
2209  if (isHeaderInsertion(R)) {
2210  // Replacements from \p Replaces must be conflict-free already, so we can
2211  // simply consume the error.
2212  llvm::consumeError(HeaderInsertions.add(R));
2213  } else if (isHeaderDeletion(R)) {
2214  HeadersToDelete.insert(R.getReplacementText());
2215  } else if (R.getOffset() == UINT_MAX) {
2216  llvm::errs() << "Insertions other than header #include insertion are "
2217  "not supported! "
2218  << R.getReplacementText() << "\n";
2219  } else {
2220  llvm::consumeError(Result.add(R));
2221  }
2222  }
2223  if (HeaderInsertions.empty() && HeadersToDelete.empty())
2224  return Replaces;
2225 
2226  StringRef FileName = Replaces.begin()->getFilePath();
2227  tooling::HeaderIncludes Includes(FileName, Code, Style.IncludeStyle);
2228 
2229  for (const auto &Header : HeadersToDelete) {
2230  tooling::Replacements Replaces =
2231  Includes.remove(Header.trim("\"<>"), Header.startswith("<"));
2232  for (const auto &R : Replaces) {
2233  auto Err = Result.add(R);
2234  if (Err) {
2235  // Ignore the deletion on conflict.
2236  llvm::errs() << "Failed to add header deletion replacement for "
2237  << Header << ": " << llvm::toString(std::move(Err))
2238  << "\n";
2239  }
2240  }
2241  }
2242 
2243  llvm::Regex IncludeRegex = llvm::Regex(CppIncludeRegexPattern);
2245  for (const auto &R : HeaderInsertions) {
2246  auto IncludeDirective = R.getReplacementText();
2247  bool Matched = IncludeRegex.match(IncludeDirective, &Matches);
2248  assert(Matched && "Header insertion replacement must have replacement text "
2249  "'#include ...'");
2250  (void)Matched;
2251  auto IncludeName = Matches[2];
2252  auto Replace =
2253  Includes.insert(IncludeName.trim("\"<>"), IncludeName.startswith("<"));
2254  if (Replace) {
2255  auto Err = Result.add(*Replace);
2256  if (Err) {
2257  llvm::consumeError(std::move(Err));
2258  unsigned NewOffset =
2259  Result.getShiftedCodePosition(Replace->getOffset());
2260  auto Shifted = tooling::Replacement(FileName, NewOffset, 0,
2261  Replace->getReplacementText());
2262  Result = Result.merge(tooling::Replacements(Shifted));
2263  }
2264  }
2265  }
2266  return Result;
2267 }
2268 
2269 } // anonymous namespace
2270 
2272 cleanupAroundReplacements(StringRef Code, const tooling::Replacements &Replaces,
2273  const FormatStyle &Style) {
2274  // We need to use lambda function here since there are two versions of
2275  // `cleanup`.
2276  auto Cleanup = [](const FormatStyle &Style, StringRef Code,
2277  std::vector<tooling::Range> Ranges,
2278  StringRef FileName) -> tooling::Replacements {
2279  return cleanup(Style, Code, Ranges, FileName);
2280  };
2281  // Make header insertion replacements insert new headers into correct blocks.
2282  tooling::Replacements NewReplaces =
2283  fixCppIncludeInsertions(Code, Replaces, Style);
2284  return processReplacements(Cleanup, Code, NewReplaces, Style);
2285 }
2286 
2287 namespace internal {
2288 std::pair<tooling::Replacements, unsigned>
2289 reformat(const FormatStyle &Style, StringRef Code,
2290  ArrayRef<tooling::Range> Ranges, unsigned FirstStartColumn,
2291  unsigned NextStartColumn, unsigned LastStartColumn, StringRef FileName,
2292  FormattingAttemptStatus *Status) {
2293  FormatStyle Expanded = expandPresets(Style);
2294  if (Expanded.DisableFormat)
2295  return {tooling::Replacements(), 0};
2296  if (isLikelyXml(Code))
2297  return {tooling::Replacements(), 0};
2298  if (Expanded.Language == FormatStyle::LK_JavaScript && isMpegTS(Code))
2299  return {tooling::Replacements(), 0};
2300 
2301  typedef std::function<std::pair<tooling::Replacements, unsigned>(
2302  const Environment &)>
2303  AnalyzerPass;
2305 
2306  if (Style.Language == FormatStyle::LK_Cpp) {
2307  if (Style.FixNamespaceComments)
2308  Passes.emplace_back([&](const Environment &Env) {
2309  return NamespaceEndCommentsFixer(Env, Expanded).process();
2310  });
2311 
2312  if (Style.SortUsingDeclarations)
2313  Passes.emplace_back([&](const Environment &Env) {
2314  return UsingDeclarationsSorter(Env, Expanded).process();
2315  });
2316  }
2317 
2318  if (Style.Language == FormatStyle::LK_JavaScript &&
2319  Style.JavaScriptQuotes != FormatStyle::JSQS_Leave)
2320  Passes.emplace_back([&](const Environment &Env) {
2321  return JavaScriptRequoter(Env, Expanded).process();
2322  });
2323 
2324  Passes.emplace_back([&](const Environment &Env) {
2325  return Formatter(Env, Expanded, Status).process();
2326  });
2327 
2328  auto Env =
2329  std::make_unique<Environment>(Code, FileName, Ranges, FirstStartColumn,
2330  NextStartColumn, LastStartColumn);
2331  llvm::Optional<std::string> CurrentCode = None;
2332  tooling::Replacements Fixes;
2333  unsigned Penalty = 0;
2334  for (size_t I = 0, E = Passes.size(); I < E; ++I) {
2335  std::pair<tooling::Replacements, unsigned> PassFixes = Passes[I](*Env);
2336  auto NewCode = applyAllReplacements(
2337  CurrentCode ? StringRef(*CurrentCode) : Code, PassFixes.first);
2338  if (NewCode) {
2339  Fixes = Fixes.merge(PassFixes.first);
2340  Penalty += PassFixes.second;
2341  if (I + 1 < E) {
2342  CurrentCode = std::move(*NewCode);
2343  Env = std::make_unique<Environment>(
2344  *CurrentCode, FileName,
2346  FirstStartColumn, NextStartColumn, LastStartColumn);
2347  }
2348  }
2349  }
2350 
2351  return {Fixes, Penalty};
2352 }
2353 } // namespace internal
2354 
2355 tooling::Replacements reformat(const FormatStyle &Style, StringRef Code,
2356  ArrayRef<tooling::Range> Ranges,
2357  StringRef FileName,
2358  FormattingAttemptStatus *Status) {
2359  return internal::reformat(Style, Code, Ranges,
2360  /*FirstStartColumn=*/0,
2361  /*NextStartColumn=*/0,
2362  /*LastStartColumn=*/0, FileName, Status)
2363  .first;
2364 }
2365 
2366 tooling::Replacements cleanup(const FormatStyle &Style, StringRef Code,
2367  ArrayRef<tooling::Range> Ranges,
2368  StringRef FileName) {
2369  // cleanups only apply to C++ (they mostly concern ctor commas etc.)
2370  if (Style.Language != FormatStyle::LK_Cpp)
2371  return tooling::Replacements();
2372  return Cleaner(Environment(Code, FileName, Ranges), Style).process().first;
2373 }
2374 
2375 tooling::Replacements reformat(const FormatStyle &Style, StringRef Code,
2376  ArrayRef<tooling::Range> Ranges,
2377  StringRef FileName, bool *IncompleteFormat) {
2378  FormattingAttemptStatus Status;
2379  auto Result = reformat(Style, Code, Ranges, FileName, &Status);
2380  if (!Status.FormatComplete)
2381  *IncompleteFormat = true;
2382  return Result;
2383 }
2384 
2386  StringRef Code,
2387  ArrayRef<tooling::Range> Ranges,
2388  StringRef FileName) {
2389  return NamespaceEndCommentsFixer(Environment(Code, FileName, Ranges), Style)
2390  .process()
2391  .first;
2392 }
2393 
2395  StringRef Code,
2396  ArrayRef<tooling::Range> Ranges,
2397  StringRef FileName) {
2398  return UsingDeclarationsSorter(Environment(Code, FileName, Ranges), Style)
2399  .process()
2400  .first;
2401 }
2402 
2404  LangOptions LangOpts;
2405  FormatStyle::LanguageStandard LexingStd =
2406  Style.Standard == FormatStyle::LS_Auto ? FormatStyle::LS_Cpp11
2407  : Style.Standard;
2408  LangOpts.CPlusPlus = 1;
2409  LangOpts.CPlusPlus11 = LexingStd >= FormatStyle::LS_Cpp11;
2410  LangOpts.CPlusPlus14 = LexingStd >= FormatStyle::LS_Cpp11;
2411  LangOpts.CPlusPlus17 = LexingStd >= FormatStyle::LS_Cpp11;
2412  LangOpts.CPlusPlus2a = LexingStd >= FormatStyle::LS_Cpp11;
2413  LangOpts.LineComment = 1;
2414  bool AlternativeOperators = Style.isCpp();
2415  LangOpts.CXXOperatorNames = AlternativeOperators ? 1 : 0;
2416  LangOpts.Bool = 1;
2417  LangOpts.ObjC = 1;
2418  LangOpts.MicrosoftExt = 1; // To get kw___try, kw___finally.
2419  LangOpts.DeclSpecKeyword = 1; // To get __declspec.
2420  return LangOpts;
2421 }
2422 
2424  "Coding style, currently supports:\n"
2425  " LLVM, Google, Chromium, Mozilla, WebKit.\n"
2426  "Use -style=file to load style configuration from\n"
2427  ".clang-format file located in one of the parent\n"
2428  "directories of the source file (or current\n"
2429  "directory for stdin).\n"
2430  "Use -style=\"{key: value, ...}\" to set specific\n"
2431  "parameters, e.g.:\n"
2432  " -style=\"{BasedOnStyle: llvm, IndentWidth: 8}\"";
2433 
2434 static FormatStyle::LanguageKind getLanguageByFileName(StringRef FileName) {
2435  if (FileName.endswith(".java"))
2436  return FormatStyle::LK_Java;
2437  if (FileName.endswith_lower(".js") || FileName.endswith_lower(".mjs") ||
2438  FileName.endswith_lower(".ts"))
2439  return FormatStyle::LK_JavaScript; // (module) JavaScript or TypeScript.
2440  if (FileName.endswith(".m") || FileName.endswith(".mm"))
2441  return FormatStyle::LK_ObjC;
2442  if (FileName.endswith_lower(".proto") ||
2443  FileName.endswith_lower(".protodevel"))
2444  return FormatStyle::LK_Proto;
2445  if (FileName.endswith_lower(".textpb") ||
2446  FileName.endswith_lower(".pb.txt") ||
2447  FileName.endswith_lower(".textproto") ||
2448  FileName.endswith_lower(".asciipb"))
2449  return FormatStyle::LK_TextProto;
2450  if (FileName.endswith_lower(".td"))
2451  return FormatStyle::LK_TableGen;
2452  if (FileName.endswith_lower(".cs"))
2453  return FormatStyle::LK_CSharp;
2454  return FormatStyle::LK_Cpp;
2455 }
2456 
2457 FormatStyle::LanguageKind guessLanguage(StringRef FileName, StringRef Code) {
2458  const auto GuessedLanguage = getLanguageByFileName(FileName);
2459  if (GuessedLanguage == FormatStyle::LK_Cpp) {
2460  auto Extension = llvm::sys::path::extension(FileName);
2461  // If there's no file extension (or it's .h), we need to check the contents
2462  // of the code to see if it contains Objective-C.
2463  if (Extension.empty() || Extension == ".h") {
2464  auto NonEmptyFileName = FileName.empty() ? "guess.h" : FileName;
2465  Environment Env(Code, NonEmptyFileName, /*Ranges=*/{});
2466  ObjCHeaderStyleGuesser Guesser(Env, getLLVMStyle());
2467  Guesser.process();
2468  if (Guesser.isObjC())
2469  return FormatStyle::LK_ObjC;
2470  }
2471  }
2472  return GuessedLanguage;
2473 }
2474 
2475 const char *DefaultFormatStyle = "file";
2476 
2477 const char *DefaultFallbackStyle = "LLVM";
2478 
2479 llvm::Expected<FormatStyle> getStyle(StringRef StyleName, StringRef FileName,
2480  StringRef FallbackStyleName,
2481  StringRef Code,
2482  llvm::vfs::FileSystem *FS) {
2483  if (!FS) {
2484  FS = llvm::vfs::getRealFileSystem().get();
2485  }
2486  FormatStyle Style = getLLVMStyle(guessLanguage(FileName, Code));
2487 
2488  FormatStyle FallbackStyle = getNoStyle();
2489  if (!getPredefinedStyle(FallbackStyleName, Style.Language, &FallbackStyle))
2490  return make_string_error("Invalid fallback style \"" + FallbackStyleName);
2491 
2492  if (StyleName.startswith("{")) {
2493  // Parse YAML/JSON style from the command line.
2494  if (std::error_code ec = parseConfiguration(StyleName, &Style))
2495  return make_string_error("Error parsing -style: " + ec.message());
2496  return Style;
2497  }
2498 
2499  if (!StyleName.equals_lower("file")) {
2500  if (!getPredefinedStyle(StyleName, Style.Language, &Style))
2501  return make_string_error("Invalid value for -style");
2502  return Style;
2503  }
2504 
2505  // Look for .clang-format/_clang-format file in the file's parent directories.
2506  SmallString<128> UnsuitableConfigFiles;
2507  SmallString<128> Path(FileName);
2508  if (std::error_code EC = FS->makeAbsolute(Path))
2509  return make_string_error(EC.message());
2510 
2511  for (StringRef Directory = Path; !Directory.empty();
2512  Directory = llvm::sys::path::parent_path(Directory)) {
2513 
2514  auto Status = FS->status(Directory);
2515  if (!Status ||
2516  Status->getType() != llvm::sys::fs::file_type::directory_file) {
2517  continue;
2518  }
2519 
2520  SmallString<128> ConfigFile(Directory);
2521 
2522  llvm::sys::path::append(ConfigFile, ".clang-format");
2523  LLVM_DEBUG(llvm::dbgs() << "Trying " << ConfigFile << "...\n");
2524 
2525  Status = FS->status(ConfigFile.str());
2526  bool FoundConfigFile =
2527  Status && (Status->getType() == llvm::sys::fs::file_type::regular_file);
2528  if (!FoundConfigFile) {
2529  // Try _clang-format too, since dotfiles are not commonly used on Windows.
2530  ConfigFile = Directory;
2531  llvm::sys::path::append(ConfigFile, "_clang-format");
2532  LLVM_DEBUG(llvm::dbgs() << "Trying " << ConfigFile << "...\n");
2533  Status = FS->status(ConfigFile.str());
2534  FoundConfigFile = Status && (Status->getType() ==
2535  llvm::sys::fs::file_type::regular_file);
2536  }
2537 
2538  if (FoundConfigFile) {
2539  llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> Text =
2540  FS->getBufferForFile(ConfigFile.str());
2541  if (std::error_code EC = Text.getError())
2542  return make_string_error(EC.message());
2543  if (std::error_code ec =
2544  parseConfiguration(Text.get()->getBuffer(), &Style)) {
2545  if (ec == ParseError::Unsuitable) {
2546  if (!UnsuitableConfigFiles.empty())
2547  UnsuitableConfigFiles.append(", ");
2548  UnsuitableConfigFiles.append(ConfigFile);
2549  continue;
2550  }
2551  return make_string_error("Error reading " + ConfigFile + ": " +
2552  ec.message());
2553  }
2554  LLVM_DEBUG(llvm::dbgs()
2555  << "Using configuration file " << ConfigFile << "\n");
2556  return Style;
2557  }
2558  }
2559  if (!UnsuitableConfigFiles.empty())
2560  return make_string_error("Configuration file(s) do(es) not support " +
2561  getLanguageName(Style.Language) + ": " +
2562  UnsuitableConfigFiles);
2563  return FallbackStyle;
2564 }
2565 
2566 } // namespace format
2567 } // namespace clang
bool IsStatic
Definition: Format.cpp:1760
StringRef Identifier
Definition: Format.cpp:1756
SourceLocation getLocWithOffset(int Offset) const
Return a source location with the specified offset from this SourceLocation.
Specialize PointerLikeTypeTraits to allow LazyGenerationalUpdatePtr to be placed into a PointerUnion...
Definition: Dominators.h:30
Token Tok
The Token.
Definition: FormatToken.h:133
tooling::Replacements sortIncludes(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName, unsigned *Cursor=nullptr)
Returns the replacements necessary to sort all #include blocks that are affected by Ranges...
Definition: Format.cpp:2122
tooling::Replacements cleanup(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Clean up any erroneous/redundant code in the given Ranges in Code.
Definition: Format.cpp:2366
Defines the SourceManager interface.
AffectedRangeManager class manages affected ranges in the code.
tooling::Replacements sortJavaImports(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName, tooling::Replacements &Replaces)
Definition: Format.cpp:2060
bool isBeforeInTranslationUnit(SourceLocation LHS, SourceLocation RHS) const
Determines the order of 2 source locations in the translation unit.
bool AlignConsecutiveDeclarations
If true, aligns consecutive declarations.
Definition: Format.h:115
static void enumeration(IO &IO, FormatStyle::BraceBreakingStyle &Value)
Definition: Format.cpp:162
static void enumeration(IO &IO, FormatStyle::DefinitionReturnTypeBreakingStyle &Value)
Definition: Format.cpp:232
llvm::Error add(const Replacement &R)
Adds a new replacement R to the current set of replacements.
FormatStyle getMozillaStyle()
Returns a format style complying with Mozilla&#39;s style guide: https://developer.mozilla.org/en-US/docs/Developer_Guide/Coding_Style.
Definition: Format.cpp:973
static void enumeration(IO &IO, FormatStyle::JavaScriptQuoteStyle &Value)
Definition: Format.cpp:91
RangeSelector name(std::string ID)
Given a node with a "name", (like NamedDecl, DeclRefExpr or CxxCtorInitializer) selects the name&#39;s to...
const AdditionalKeywords & getKeywords()
static std::pair< unsigned, unsigned > FindCursorIndex(const SmallVectorImpl< IncludeDirective > &Includes, const SmallVectorImpl< unsigned > &Indices, unsigned Cursor)
Definition: Format.cpp:1784
std::error_code make_error_code(ParseError e)
Definition: Format.cpp:593
bool isLikelyXml(StringRef Code)
Definition: Format.cpp:2120
StringRef getBufferData(FileID FID, bool *Invalid=nullptr) const
Return a StringRef to the source buffer data for the specified FileID.
Maintains a set of replacements that are conflict-free.
Definition: Replacement.h:209
tooling::Replacements fixNamespaceEndComments(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Fix namespace end comments in the given Ranges in Code.
Definition: Format.cpp:2385
unsigned getShiftedCodePosition(unsigned Position) const
FormatToken * Next
The next token in the unwrapped line.
Definition: FormatToken.h:298
FormatStyle getWebKitStyle()
Returns a format style complying with Webkit&#39;s style guide: http://www.webkit.org/coding/coding-style...
Definition: Format.cpp:999
LLVM_NODISCARD Replacements merge(const Replacements &Replaces) const
Merges Replaces into the current replacements.
bool applyAllReplacements(const Replacements &Replaces, Rewriter &Rewrite)
Apply all replacements in Replaces to the Rewriter Rewrite.
FormatStyle getLLVMStyle(FormatStyle::LanguageKind Language=FormatStyle::LanguageKind::LK_Cpp)
Returns a format style complying with the LLVM coding standards: http://llvm.org/docs/CodingStandards...
Definition: Format.cpp:673
This file declares Format APIs to be used internally by the formatting library implementation.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
EscapedNewlineAlignmentStyle AlignEscapedNewlines
Options for aligning backslashes in escaped newlines.
Definition: Format.h:149
Definition: Format.h:2327
FormatToken * Previous
The previous token in the unwrapped line.
Definition: FormatToken.h:295
static void enumeration(IO &IO, FormatStyle::ShortIfStyle &Value)
Definition: Format.cpp:121
This file implements a token annotator, i.e.
static void enumeration(IO &IO, FormatStyle::PointerAlignmentStyle &Value)
Definition: Format.cpp:280
std::pair< tooling::Replacements, unsigned > reformat(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, unsigned FirstStartColumn, unsigned NextStartColumn, unsigned LastStartColumn, StringRef FileName, FormattingAttemptStatus *Status)
Reformats the given Ranges in the code fragment Code.
Definition: Format.cpp:2289
int Category
Definition: Format.cpp:1752
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:49
Manages the whitespaces around tokens and their replacements.
static llvm::Expected< tooling::Replacements > processReplacements(T ProcessFunc, StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Definition: Format.cpp:2143
This file contains FormatTokenLexer, which tokenizes a source file into a token stream suitable for C...
bool isNot(T Kind) const
Definition: FormatToken.h:328
const FormatToken & Tok
static void enumeration(IO &IO, FormatStyle::LanguageKind &Value)
Definition: Format.cpp:56
FormatStyle::LanguageKind guessLanguage(StringRef FileName, StringRef Code)
Definition: Format.cpp:2457
llvm::Error Error
Defines the Diagnostic-related interfaces.
static void enumeration(IO &IO, FormatStyle::BinaryOperatorStyle &Value)
Definition: Format.cpp:152
FormatStyle getChromiumStyle(FormatStyle::LanguageKind Language)
Returns a format style complying with Chromium&#39;s style guide: http://www.chromium.org/developers/coding-style.
Definition: Format.cpp:913
static size_t size(IO &IO, std::vector< FormatStyle > &Seq)
Definition: Format.cpp:564
FormatStyle getGNUStyle()
Returns a format style complying with GNU Coding Standards: http://www.gnu.org/prep/standards/standar...
Definition: Format.cpp:1022
#define UINT_MAX
Definition: limits.h:56
bool isMpegTS(StringRef Code)
Definition: Format.cpp:2113
const SourceManager & getSourceManager() const
Definition: TokenAnalyzer.h:49
static void enumeration(IO &IO, FormatStyle::ShortFunctionStyle &Value)
Definition: Format.cpp:109
bool AlignConsecutiveAssignments
If true, aligns consecutive assignments.
Definition: Format.h:104
Generates replacements for inserting or deleting #include directives in a file.
static void enumeration(IO &IO, FormatStyle::ShortLambdaStyle &Value)
Definition: Format.cpp:133
unsigned getLastStartColumn() const
Definition: TokenAnalyzer.h:63
Language
The language for the input, used to select and validate the language standard and possible actions...
Definition: LangStandard.h:19
llvm::Expected< tooling::Replacements > formatReplacements(StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Returns the replacements corresponding to applying and formatting Replaces on success; otheriwse...
Definition: Format.cpp:2162
BracketAlignmentStyle AlignAfterOpenBracket
If true, horizontally aligns arguments after an open bracket.
Definition: Format.h:80
A text replacement.
Definition: Replacement.h:83
tooling::Replacements sortUsingDeclarations(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName="<stdin>")
Sort consecutive using declarations in the given Ranges in Code.
Definition: Format.cpp:2394
StringRef Filename
Definition: Format.cpp:1749
static void enumeration(IO &IO, FormatStyle::EscapedNewlineAlignmentStyle &Value)
Definition: Format.cpp:267
WhitespaceManager class manages whitespace around tokens and their replacements.
unsigned Offset
Definition: Format.cpp:1751
static void enumeration(IO &IO, FormatStyle::SpaceBeforeParensOptions &Value)
Definition: Format.cpp:293
Determines extra information about the tokens comprising an UnwrappedLine.
SourceLocation End
ContinuationIndenter * Indenter
const AnnotatedLine * Line
LangOptions getFormattingLangOpts(const FormatStyle &Style=getLLVMStyle())
Returns the LangOpts that the formatter expects you to set.
Definition: Format.cpp:2403
static void mapping(IO &IO, FormatStyle::BraceWrappingFlags &Wrapping)
Definition: Format.cpp:528
llvm::Optional< tooling::Replacement > insert(llvm::StringRef Header, bool IsAngled) const
Inserts an #include directive of Header into the code.
ParameterPackingKind PackingKind
If this is an opening parenthesis, how are the parameters packed?
Definition: FormatToken.h:212
SourceLocation getLocation() const
Return a source location identifier for the specified offset in the current file. ...
Definition: Token.h:126
bool AlignOperands
If true, horizontally align operands of binary and ternary expressions.
Definition: Format.h:160
A wrapper around a Token storing information about the whitespace characters preceding it...
Definition: FormatToken.h:129
void setCommentLineLevels(SmallVectorImpl< AnnotatedLine *> &Lines)
Adapts the indent levels of comment lines to the indent of the subsequent line.
int AccessModifierOffset
The extra indent or outdent of access modifiers, e.g. public:.
Definition: Format.h:51
SourceLocation getEnd() const
This class manages priorities of C++ #include categories and calculates priorities for headers...
FormatStyle getGoogleStyle(FormatStyle::LanguageKind Language)
Returns a format style complying with one of Google&#39;s style guides: http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml.
Definition: Format.cpp:788
Implements a combinartorial exploration of all the different linebreaks unwrapped lines can be format...
static void enumeration(IO &IO, FormatStyle::BinPackStyle &Value)
Definition: Format.cpp:144
static void enumeration(IO &IO, FormatStyle::LanguageStandard &Value)
Definition: Format.cpp:69
const SourceManager & SM
Definition: Format.cpp:1609
const_iterator begin() const
Definition: Replacement.h:278
const char * DefaultFallbackStyle
The suggested predefined style to use as the fallback style in getStyle.
Definition: Format.cpp:2477
llvm::Expected< tooling::Replacements > cleanupAroundReplacements(StringRef Code, const tooling::Replacements &Replaces, const FormatStyle &Style)
Returns the replacements corresponding to applying Replaces and cleaning up the code after that on su...
Definition: Format.cpp:2272
StringRef getLanguageName(FormatStyle::LanguageKind Language)
Definition: Format.h:2301
const char * getTokenTypeName(TokenType Type)
Determines the name of a token type.
Definition: FormatToken.cpp:24
static void enumeration(IO &IO, FormatStyle::BreakTemplateDeclarationsStyle &Value)
Definition: Format.cpp:217
Encodes a location in the source.
bool is(tok::TokenKind Kind) const
Definition: FormatToken.h:312
FormatStyle getMicrosoftStyle(FormatStyle::LanguageKind Language)
Definition: Format.cpp:1037
std::vector< StringRef > AssociatedCommentLines
Definition: Format.cpp:1759
Various functions to configurably format source code.
static void enumeration(IO &IO, FormatStyle::ReturnTypeBreakingStyle &Value)
Definition: Format.cpp:205
SourceRange WhitespaceRange
The range of the whitespace immediately preceding the Token.
Definition: FormatToken.h:146
This file contains the declaration of the UnwrappedLineParser, which turns a stream of tokens into Un...
const char * DefaultFormatStyle
The suggested format style to use by default.
Definition: Format.cpp:2475
static void enumeration(IO &IO, FormatStyle::NamespaceIndentationKind &Value)
Definition: Format.cpp:245
bool FormatComplete
A value of false means that any of the affected ranges were not formatted due to a non-recoverable sy...
Definition: Format.h:2189
llvm::Error make_string_error(const llvm::Twine &Message)
Definition: Format.cpp:597
unsigned getLength() const
Definition: Replacement.h:122
The FormatStyle is used to configure the formatting to follow specific guidelines.
Definition: Format.h:49
static void enumeration(IO &IO, FormatStyle::UseTabStyle &Value)
Definition: Format.cpp:79
static void enumeration(IO &IO, FormatStyle::PPDirectiveIndentStyle &Value)
Definition: Format.cpp:196
std::string configurationAsText(const FormatStyle &Style)
Gets configuration in a YAML string.
Definition: Format.cpp:1150
std::vector< Range > getAffectedRanges() const
const char * StyleOptionHelpDescription
Description to be used for help text for a llvm::cl option for specifying format style.
Definition: Format.cpp:2423
static unsigned findJavaImportGroup(const FormatStyle &Style, StringRef ImportIdentifier)
Definition: Format.cpp:1966
Represents the status of a formatting attempt.
Definition: Format.h:2186
Dataflow Directional Tag Classes.
std::pair< tooling::Replacements, unsigned > process()
This file implements a sorter for JavaScript ES6 imports.
unsigned getOffset() const
Definition: Replacement.h:121
static void enumeration(IO &IO, FormatStyle::BreakConstructorInitializersStyle &Value)
Definition: Format.cpp:177
static void enumeration(IO &IO, FormatStyle::ShortBlockStyle &Value)
Definition: Format.cpp:99
void calculateFormattingInformation(AnnotatedLine &Line)
static FormatStyle::LanguageKind getLanguageByFileName(StringRef FileName)
Definition: Format.cpp:2434
bool getPredefinedStyle(StringRef Name, FormatStyle::LanguageKind Language, FormatStyle *Style)
Gets a predefined style for the specified language by name.
Definition: Format.cpp:1070
bool AlignConsecutiveMacros
If true, aligns consecutive C/C++ preprocessor macros.
Definition: Format.h:93
static void enumeration(IO &IO, FormatStyle::BreakInheritanceListStyle &Value)
Definition: Format.cpp:186
static void enumeration(IO &IO, FormatStyle::BracketAlignmentStyle &Value)
Definition: Format.cpp:254
FormatStyle getNoStyle()
Returns style indicating formatting should be not applied at all.
Definition: Format.cpp:1062
int getIncludePriority(StringRef IncludeName, bool CheckMainHeader) const
Returns the priority of the category which IncludeName belongs to.
bool startsWithNamespace() const
true if this line starts a namespace definition.
This file declares an abstract TokenAnalyzer, and associated helper classes.
static void mapping(IO &IO, FormatStyle::RawStringFormat &Format)
Definition: Format.cpp:549
static FormatStyle expandPresets(const FormatStyle &Style)
Definition: Format.cpp:618
const std::error_category & getParseCategory()
Definition: Format.cpp:589
tooling::Replacements sortCppIncludes(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName, tooling::Replacements &Replaces, unsigned *Cursor)
Definition: Format.cpp:1895
llvm::Expected< FormatStyle > getStyle(StringRef StyleName, StringRef FileName, StringRef FallbackStyle, StringRef Code="", llvm::vfs::FileSystem *FS=nullptr)
Construct a FormatStyle based on StyleName.
Definition: Format.cpp:2479
bool Add(InterpState &S, CodePtr OpPC)
Definition: Interp.h:132
unsigned getFirstStartColumn() const
Definition: TokenAnalyzer.h:55
static bool affectsRange(ArrayRef< tooling::Range > Ranges, unsigned Start, unsigned End)
Definition: Format.cpp:1766
bool AlignTrailingComments
If true, aligns trailing comments.
Definition: Format.h:168
StringRef Text
Definition: Format.cpp:1750
static void mapping(IO &IO, FormatStyle &Style)
Definition: Format.cpp:309
std::error_code parseConfiguration(StringRef Text, FormatStyle *Style)
Parse configuration from YAML-formatted text.
Definition: Format.cpp:1096
std::vector< Range > calculateRangesAfterReplacements(const Replacements &Replaces, const std::vector< Range > &Ranges)
Calculates the new ranges after Replaces are applied.
This file implements an indenter that manages the indentation of continuations.
tooling::Replacements remove(llvm::StringRef Header, bool IsAngled) const
Removes all existing #includes of Header quoted with <> if IsAngled is true or "" if IsAngled is fals...
tooling::Replacements sortJavaScriptImports(const FormatStyle &Style, StringRef Code, ArrayRef< tooling::Range > Ranges, StringRef FileName)
unsigned getNextStartColumn() const
Definition: TokenAnalyzer.h:59
This file declares UsingDeclarationsSorter, a TokenAnalyzer that sorts consecutive using declarations...
This file declares NamespaceEndCommentsFixer, a TokenAnalyzer that fixes namespace end comments...
StringRef getReplacementText() const
Definition: Replacement.h:123
SourceLocation getBegin() const
This class handles loading and caching of source files into memory.
static FormatStyle & element(IO &IO, std::vector< FormatStyle > &Seq, size_t Index)
Definition: Format.cpp:567
bool isObjC(ID Id)
isObjC - Is this an "ObjC" input (Obj-C and Obj-C++ sources and headers).
Definition: Types.cpp:147
bool AllowAllArgumentsOnNextLine
If a function call or braced initializer list doesn&#39;t fit on a line, allow putting all arguments onto...
Definition: Format.h:184
const FormatStyle & Style
SourceLocation getEndLoc() const
Definition: Token.h:153