annotate clang/lib/Format/Format.cpp @ 176:de4ac79aef9d

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