]> CyberLeo.Net >> Repos - FreeBSD/releng/10.2.git/blob - contrib/llvm/tools/clang/lib/Format/ContinuationIndenter.h
- Copy stable/10@285827 to releng/10.2 in preparation for 10.2-RC1
[FreeBSD/releng/10.2.git] / contrib / llvm / tools / clang / lib / Format / ContinuationIndenter.h
1 //===--- ContinuationIndenter.h - Format C++ code ---------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 ///
10 /// \file
11 /// \brief This file implements an indenter that manages the indentation of
12 /// continuations.
13 ///
14 //===----------------------------------------------------------------------===//
15
16 #ifndef LLVM_CLANG_FORMAT_CONTINUATION_INDENTER_H
17 #define LLVM_CLANG_FORMAT_CONTINUATION_INDENTER_H
18
19 #include "Encoding.h"
20 #include "clang/Format/Format.h"
21
22 namespace clang {
23 class SourceManager;
24
25 namespace format {
26
27 class AnnotatedLine;
28 struct FormatToken;
29 struct LineState;
30 struct ParenState;
31 class WhitespaceManager;
32
33 class ContinuationIndenter {
34 public:
35   /// \brief Constructs a \c ContinuationIndenter to format \p Line starting in
36   /// column \p FirstIndent.
37   ContinuationIndenter(const FormatStyle &Style, SourceManager &SourceMgr,
38                        WhitespaceManager &Whitespaces,
39                        encoding::Encoding Encoding,
40                        bool BinPackInconclusiveFunctions);
41
42   /// \brief Get the initial state, i.e. the state after placing \p Line's
43   /// first token at \p FirstIndent.
44   LineState getInitialState(unsigned FirstIndent, const AnnotatedLine *Line,
45                             bool DryRun);
46
47   // FIXME: canBreak and mustBreak aren't strictly indentation-related. Find a
48   // better home.
49   /// \brief Returns \c true, if a line break after \p State is allowed.
50   bool canBreak(const LineState &State);
51
52   /// \brief Returns \c true, if a line break after \p State is mandatory.
53   bool mustBreak(const LineState &State);
54
55   /// \brief Appends the next token to \p State and updates information
56   /// necessary for indentation.
57   ///
58   /// Puts the token on the current line if \p Newline is \c false and adds a
59   /// line break and necessary indentation otherwise.
60   ///
61   /// If \p DryRun is \c false, also creates and stores the required
62   /// \c Replacement.
63   unsigned addTokenToState(LineState &State, bool Newline, bool DryRun,
64                            unsigned ExtraSpaces = 0);
65
66   /// \brief Get the column limit for this line. This is the style's column
67   /// limit, potentially reduced for preprocessor definitions.
68   unsigned getColumnLimit(const LineState &State) const;
69
70 private:
71   /// \brief Mark the next token as consumed in \p State and modify its stacks
72   /// accordingly.
73   unsigned moveStateToNextToken(LineState &State, bool DryRun, bool Newline);
74
75   /// \brief If the current token sticks out over the end of the line, break
76   /// it if possible.
77   ///
78   /// \returns An extra penalty if a token was broken, otherwise 0.
79   ///
80   /// The returned penalty will cover the cost of the additional line breaks and
81   /// column limit violation in all lines except for the last one. The penalty
82   /// for the column limit violation in the last line (and in single line
83   /// tokens) is handled in \c addNextStateToQueue.
84   unsigned breakProtrudingToken(const FormatToken &Current, LineState &State,
85                                 bool DryRun);
86
87   /// \brief Appends the next token to \p State and updates information
88   /// necessary for indentation.
89   ///
90   /// Puts the token on the current line.
91   ///
92   /// If \p DryRun is \c false, also creates and stores the required
93   /// \c Replacement.
94   void addTokenOnCurrentLine(LineState &State, bool DryRun,
95                              unsigned ExtraSpaces);
96
97   /// \brief Appends the next token to \p State and updates information
98   /// necessary for indentation.
99   ///
100   /// Adds a line break and necessary indentation.
101   ///
102   /// If \p DryRun is \c false, also creates and stores the required
103   /// \c Replacement.
104   unsigned addTokenOnNewLine(LineState &State, bool DryRun);
105
106   /// \brief Adds a multiline token to the \p State.
107   ///
108   /// \returns Extra penalty for the first line of the literal: last line is
109   /// handled in \c addNextStateToQueue, and the penalty for other lines doesn't
110   /// matter, as we don't change them.
111   unsigned addMultilineToken(const FormatToken &Current, LineState &State);
112
113   /// \brief Returns \c true if the next token starts a multiline string
114   /// literal.
115   ///
116   /// This includes implicitly concatenated strings, strings that will be broken
117   /// by clang-format and string literals with escaped newlines.
118   bool NextIsMultilineString(const LineState &State);
119
120   FormatStyle Style;
121   SourceManager &SourceMgr;
122   WhitespaceManager &Whitespaces;
123   encoding::Encoding Encoding;
124   bool BinPackInconclusiveFunctions;
125 };
126
127 struct ParenState {
128   ParenState(unsigned Indent, unsigned IndentLevel, unsigned LastSpace,
129              bool AvoidBinPacking, bool NoLineBreak)
130       : Indent(Indent), IndentLevel(IndentLevel), LastSpace(LastSpace),
131         FirstLessLess(0), BreakBeforeClosingBrace(false), QuestionColumn(0),
132         AvoidBinPacking(AvoidBinPacking), BreakBeforeParameter(false),
133         NoLineBreak(NoLineBreak), ColonPos(0), StartOfFunctionCall(0),
134         StartOfArraySubscripts(0), NestedNameSpecifierContinuation(0),
135         CallContinuation(0), VariablePos(0), ContainsLineBreak(false),
136         ContainsUnwrappedBuilder(0) {}
137
138   /// \brief The position to which a specific parenthesis level needs to be
139   /// indented.
140   unsigned Indent;
141
142   /// \brief The number of indentation levels of the block.
143   unsigned IndentLevel;
144
145   /// \brief The position of the last space on each level.
146   ///
147   /// Used e.g. to break like:
148   /// functionCall(Parameter, otherCall(
149   ///                             OtherParameter));
150   unsigned LastSpace;
151
152   /// \brief The position the first "<<" operator encountered on each level.
153   ///
154   /// Used to align "<<" operators. 0 if no such operator has been encountered
155   /// on a level.
156   unsigned FirstLessLess;
157
158   /// \brief Whether a newline needs to be inserted before the block's closing
159   /// brace.
160   ///
161   /// We only want to insert a newline before the closing brace if there also
162   /// was a newline after the beginning left brace.
163   bool BreakBeforeClosingBrace;
164
165   /// \brief The column of a \c ? in a conditional expression;
166   unsigned QuestionColumn;
167
168   /// \brief Avoid bin packing, i.e. multiple parameters/elements on multiple
169   /// lines, in this context.
170   bool AvoidBinPacking;
171
172   /// \brief Break after the next comma (or all the commas in this context if
173   /// \c AvoidBinPacking is \c true).
174   bool BreakBeforeParameter;
175
176   /// \brief Line breaking in this context would break a formatting rule.
177   bool NoLineBreak;
178
179   /// \brief The position of the colon in an ObjC method declaration/call.
180   unsigned ColonPos;
181
182   /// \brief The start of the most recent function in a builder-type call.
183   unsigned StartOfFunctionCall;
184
185   /// \brief Contains the start of array subscript expressions, so that they
186   /// can be aligned.
187   unsigned StartOfArraySubscripts;
188
189   /// \brief If a nested name specifier was broken over multiple lines, this
190   /// contains the start column of the second line. Otherwise 0.
191   unsigned NestedNameSpecifierContinuation;
192
193   /// \brief If a call expression was broken over multiple lines, this
194   /// contains the start column of the second line. Otherwise 0.
195   unsigned CallContinuation;
196
197   /// \brief The column of the first variable name in a variable declaration.
198   ///
199   /// Used to align further variables if necessary.
200   unsigned VariablePos;
201
202   /// \brief \c true if this \c ParenState already contains a line-break.
203   ///
204   /// The first line break in a certain \c ParenState causes extra penalty so
205   /// that clang-format prefers similar breaks, i.e. breaks in the same
206   /// parenthesis.
207   bool ContainsLineBreak;
208
209   /// \brief \c true if this \c ParenState contains multiple segments of a
210   /// builder-type call on one line.
211   bool ContainsUnwrappedBuilder;
212
213   bool operator<(const ParenState &Other) const {
214     if (Indent != Other.Indent)
215       return Indent < Other.Indent;
216     if (LastSpace != Other.LastSpace)
217       return LastSpace < Other.LastSpace;
218     if (FirstLessLess != Other.FirstLessLess)
219       return FirstLessLess < Other.FirstLessLess;
220     if (BreakBeforeClosingBrace != Other.BreakBeforeClosingBrace)
221       return BreakBeforeClosingBrace;
222     if (QuestionColumn != Other.QuestionColumn)
223       return QuestionColumn < Other.QuestionColumn;
224     if (AvoidBinPacking != Other.AvoidBinPacking)
225       return AvoidBinPacking;
226     if (BreakBeforeParameter != Other.BreakBeforeParameter)
227       return BreakBeforeParameter;
228     if (NoLineBreak != Other.NoLineBreak)
229       return NoLineBreak;
230     if (ColonPos != Other.ColonPos)
231       return ColonPos < Other.ColonPos;
232     if (StartOfFunctionCall != Other.StartOfFunctionCall)
233       return StartOfFunctionCall < Other.StartOfFunctionCall;
234     if (StartOfArraySubscripts != Other.StartOfArraySubscripts)
235       return StartOfArraySubscripts < Other.StartOfArraySubscripts;
236     if (CallContinuation != Other.CallContinuation)
237       return CallContinuation < Other.CallContinuation;
238     if (VariablePos != Other.VariablePos)
239       return VariablePos < Other.VariablePos;
240     if (ContainsLineBreak != Other.ContainsLineBreak)
241       return ContainsLineBreak < Other.ContainsLineBreak;
242     if (ContainsUnwrappedBuilder != Other.ContainsUnwrappedBuilder)
243       return ContainsUnwrappedBuilder < Other.ContainsUnwrappedBuilder;
244     return false;
245   }
246 };
247
248 /// \brief The current state when indenting a unwrapped line.
249 ///
250 /// As the indenting tries different combinations this is copied by value.
251 struct LineState {
252   /// \brief The number of used columns in the current line.
253   unsigned Column;
254
255   /// \brief The token that needs to be next formatted.
256   FormatToken *NextToken;
257
258   /// \brief \c true if this line contains a continued for-loop section.
259   bool LineContainsContinuedForLoopSection;
260
261   /// \brief The level of nesting inside (), [], <> and {}.
262   unsigned ParenLevel;
263
264   /// \brief The \c ParenLevel at the start of this line.
265   unsigned StartOfLineLevel;
266
267   /// \brief The lowest \c ParenLevel on the current line.
268   unsigned LowestLevelOnLine;
269
270   /// \brief The start column of the string literal, if we're in a string
271   /// literal sequence, 0 otherwise.
272   unsigned StartOfStringLiteral;
273
274   /// \brief A stack keeping track of properties applying to parenthesis
275   /// levels.
276   std::vector<ParenState> Stack;
277
278   /// \brief Ignore the stack of \c ParenStates for state comparison.
279   ///
280   /// In long and deeply nested unwrapped lines, the current algorithm can
281   /// be insufficient for finding the best formatting with a reasonable amount
282   /// of time and memory. Setting this flag will effectively lead to the
283   /// algorithm not analyzing some combinations. However, these combinations
284   /// rarely contain the optimal solution: In short, accepting a higher
285   /// penalty early would need to lead to different values in the \c
286   /// ParenState stack (in an otherwise identical state) and these different
287   /// values would need to lead to a significant amount of avoided penalty
288   /// later.
289   ///
290   /// FIXME: Come up with a better algorithm instead.
291   bool IgnoreStackForComparison;
292
293   /// \brief The indent of the first token.
294   unsigned FirstIndent;
295
296   /// \brief The line that is being formatted.
297   ///
298   /// Does not need to be considered for memoization because it doesn't change.
299   const AnnotatedLine *Line;
300
301   /// \brief Comparison operator to be able to used \c LineState in \c map.
302   bool operator<(const LineState &Other) const {
303     if (NextToken != Other.NextToken)
304       return NextToken < Other.NextToken;
305     if (Column != Other.Column)
306       return Column < Other.Column;
307     if (LineContainsContinuedForLoopSection !=
308         Other.LineContainsContinuedForLoopSection)
309       return LineContainsContinuedForLoopSection;
310     if (ParenLevel != Other.ParenLevel)
311       return ParenLevel < Other.ParenLevel;
312     if (StartOfLineLevel != Other.StartOfLineLevel)
313       return StartOfLineLevel < Other.StartOfLineLevel;
314     if (LowestLevelOnLine != Other.LowestLevelOnLine)
315       return LowestLevelOnLine < Other.LowestLevelOnLine;
316     if (StartOfStringLiteral != Other.StartOfStringLiteral)
317       return StartOfStringLiteral < Other.StartOfStringLiteral;
318     if (IgnoreStackForComparison || Other.IgnoreStackForComparison)
319       return false;
320     return Stack < Other.Stack;
321   }
322 };
323
324 } // end namespace format
325 } // end namespace clang
326
327 #endif // LLVM_CLANG_FORMAT_CONTINUATION_INDENTER_H