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