1 // astyle.h
2 // Copyright (c) 2017 by Jim Pattee <jimp03@email.com>.
3 // This code is licensed under the MIT License.
4 // License.md describes the conditions under which this software may be distributed.
5 
6 #ifndef ASTYLE_H
7 #define ASTYLE_H
8 
9 //-----------------------------------------------------------------------------
10 // headers
11 //-----------------------------------------------------------------------------
12 
13 #ifdef __VMS
14 	#define __USE_STD_IOSTREAM 1
15 	#include <assert>
16 #else
17 	#include <cassert>
18 #endif
19 
20 #include <cctype>
21 #include <iostream>		// for cout
22 #include <memory>
23 #include <string>
24 #include <vector>
25 
26 #ifdef __GNUC__
27 	#include <cstring>              // need both string and cstring for GCC
28 #endif
29 
30 //-----------------------------------------------------------------------------
31 // declarations
32 //-----------------------------------------------------------------------------
33 
34 #ifdef _MSC_VER
35 	#pragma warning(disable: 4267)  // conversion from size_t to int
36 #endif
37 
38 #ifdef __BORLANDC__
39 	#pragma warn -8004	            // variable is assigned a value that is never used
40 #endif
41 
42 #ifdef __GNUC__
43 	#pragma GCC diagnostic ignored "-Wconversion"
44 #endif
45 
46 #ifdef __INTEL_COMPILER
47 	#pragma warning(disable:  383)  // value copied to temporary, reference to temporary used
48 	#pragma warning(disable:  981)  // operands are evaluated in unspecified order
49 #endif
50 
51 #ifdef __clang__
52 	#pragma clang diagnostic ignored "-Wshorten-64-to-32"
53 #endif
54 
55 //-----------------------------------------------------------------------------
56 // astyle namespace
57 //-----------------------------------------------------------------------------
58 
59 namespace astyle {
60 //
61 using namespace std;
62 
63 //----------------------------------------------------------------------------
64 // definitions
65 //----------------------------------------------------------------------------
66 
67 enum FileType { C_TYPE = 0, JAVA_TYPE = 1, SHARP_TYPE = 2 };
68 
69 /* The enums below are not recognized by 'vectors' in Microsoft Visual C++
70    V5 when they are part of a namespace!!!  Use Visual C++ V6 or higher.
71 */
72 enum FormatStyle
73 {
74 	STYLE_NONE,
75 	STYLE_ALLMAN,
76 	STYLE_JAVA,
77 	STYLE_KR,
78 	STYLE_STROUSTRUP,
79 	STYLE_WHITESMITH,
80 	STYLE_VTK,
81 	STYLE_BANNER,
82 	STYLE_GNU,
83 	STYLE_LINUX,
84 	STYLE_HORSTMANN,
85 	STYLE_1TBS,
86 	STYLE_GOOGLE,
87 	STYLE_MOZILLA,
88 	STYLE_PICO,
89 	STYLE_LISP
90 };
91 
92 enum BraceMode
93 {
94 	NONE_MODE,
95 	ATTACH_MODE,
96 	BREAK_MODE,
97 	LINUX_MODE,
98 	RUN_IN_MODE		// broken braces
99 };
100 
101 // maximun value for int is 16,384 (total value of 32,767)
102 enum BraceType
103 {
104 	NULL_TYPE        = 0,
105 	NAMESPACE_TYPE   = 1,		// also a DEFINITION_TYPE
106 	CLASS_TYPE       = 2,		// also a DEFINITION_TYPE
107 	STRUCT_TYPE      = 4,		// also a DEFINITION_TYPE
108 	INTERFACE_TYPE   = 8,		// also a DEFINITION_TYPE
109 	DEFINITION_TYPE  = 16,
110 	COMMAND_TYPE     = 32,
111 	ARRAY_NIS_TYPE   = 64,		// also an ARRAY_TYPE
112 	ENUM_TYPE        = 128,		// also an ARRAY_TYPE
113 	INIT_TYPE        = 256,		// also an ARRAY_TYPE
114 	ARRAY_TYPE       = 512,
115 	EXTERN_TYPE      = 1024,	// extern "C", not a command type extern
116 	EMPTY_BLOCK_TYPE = 2048,	// also a SINGLE_LINE_TYPE
117 	BREAK_BLOCK_TYPE = 4096,	// also a SINGLE_LINE_TYPE
118 	SINGLE_LINE_TYPE = 8192
119 };
120 
121 enum MinConditional
122 {
123 	MINCOND_ZERO,
124 	MINCOND_ONE,
125 	MINCOND_TWO,
126 	MINCOND_ONEHALF,
127 	MINCOND_END
128 };
129 
130 enum ObjCColonPad
131 {
132 	COLON_PAD_NO_CHANGE,
133 	COLON_PAD_NONE,
134 	COLON_PAD_ALL,
135 	COLON_PAD_AFTER,
136 	COLON_PAD_BEFORE
137 };
138 
139 enum PointerAlign
140 {
141 	PTR_ALIGN_NONE,
142 	PTR_ALIGN_TYPE,
143 	PTR_ALIGN_MIDDLE,
144 	PTR_ALIGN_NAME
145 };
146 
147 enum ReferenceAlign
148 {
149 	REF_ALIGN_NONE   = PTR_ALIGN_NONE,
150 	REF_ALIGN_TYPE   = PTR_ALIGN_TYPE,
151 	REF_ALIGN_MIDDLE = PTR_ALIGN_MIDDLE,
152 	REF_ALIGN_NAME   = PTR_ALIGN_NAME,
153 	REF_SAME_AS_PTR
154 };
155 
156 enum FileEncoding
157 {
158 	ENCODING_8BIT,
159 	UTF_16BE,
160 	UTF_16LE,     // Windows default
161 	UTF_32BE,
162 	UTF_32LE
163 };
164 
165 enum LineEndFormat
166 {
167 	LINEEND_DEFAULT,	// Use line break that matches most of the file
168 	LINEEND_WINDOWS,
169 	LINEEND_LINUX,
170 	LINEEND_MACOLD,
171 	LINEEND_CRLF = LINEEND_WINDOWS,
172 	LINEEND_LF   = LINEEND_LINUX,
173 	LINEEND_CR   = LINEEND_MACOLD
174 };
175 
176 //-----------------------------------------------------------------------------
177 // Class ASSourceIterator
178 // A pure virtual class is used by ASFormatter and ASBeautifier instead of
179 // ASStreamIterator. This allows programs using AStyle as a plug-in to define
180 // their own ASStreamIterator. The ASStreamIterator class must inherit
181 // this class.
182 //-----------------------------------------------------------------------------
183 
184 class ASSourceIterator
185 {
186 public:
ASSourceIterator()187 	ASSourceIterator() {}
~ASSourceIterator()188 	virtual ~ASSourceIterator() {}
189 	virtual int getStreamLength() const = 0;
190 	virtual bool hasMoreLines() const = 0;
191 	virtual string nextLine(bool emptyLineWasDeleted = false) = 0;
192 	virtual string peekNextLine() = 0;
193 	virtual void peekReset() = 0;
194 	virtual streamoff tellg() = 0;
195 };
196 
197 //-----------------------------------------------------------------------------
198 // Class ASPeekStream
199 // A small class using RAII to peek ahead in the ASSourceIterator stream
200 // and to reset the ASSourceIterator pointer in the destructor.
201 // It enables a return from anywhere in the method.
202 //-----------------------------------------------------------------------------
203 
204 class ASPeekStream
205 {
206 private:
207 	ASSourceIterator* sourceIterator;
208 	bool needReset;		// reset sourceIterator to the original position
209 
210 public:
ASPeekStream(ASSourceIterator * sourceIterator_)211 	explicit ASPeekStream(ASSourceIterator* sourceIterator_)
212 	{ sourceIterator = sourceIterator_; needReset = false; }
213 
~ASPeekStream()214 	~ASPeekStream()
215 	{ if (needReset) sourceIterator->peekReset(); }
216 
hasMoreLines()217 	bool hasMoreLines() const
218 	{ return sourceIterator->hasMoreLines(); }
219 
peekNextLine()220 	string peekNextLine()
221 	{ needReset = true; return sourceIterator->peekNextLine(); }
222 };
223 
224 
225 //-----------------------------------------------------------------------------
226 // Class ASResource
227 //-----------------------------------------------------------------------------
228 
229 class ASResource
230 {
231 public:
232 	void buildAssignmentOperators(vector<const string*>* assignmentOperators);
233 	void buildCastOperators(vector<const string*>* castOperators);
234 	void buildHeaders(vector<const string*>* headers, int fileType, bool beautifier = false);
235 	void buildIndentableMacros(vector<const pair<const string, const string>* >* indentableMacros);
236 	void buildIndentableHeaders(vector<const string*>* indentableHeaders);
237 	void buildNonAssignmentOperators(vector<const string*>* nonAssignmentOperators);
238 	void buildNonParenHeaders(vector<const string*>* nonParenHeaders, int fileType, bool beautifier = false);
239 	void buildOperators(vector<const string*>* operators, int fileType);
240 	void buildPreBlockStatements(vector<const string*>* preBlockStatements, int fileType);
241 	void buildPreCommandHeaders(vector<const string*>* preCommandHeaders, int fileType);
242 	void buildPreDefinitionHeaders(vector<const string*>* preDefinitionHeaders, int fileType);
243 
244 public:
245 	static const string AS_IF, AS_ELSE;
246 	static const string AS_DO, AS_WHILE;
247 	static const string AS_FOR;
248 	static const string AS_SWITCH, AS_CASE, AS_DEFAULT;
249 	static const string AS_TRY, AS_CATCH, AS_THROW, AS_THROWS, AS_FINALLY, AS_USING;
250 	static const string _AS_TRY, _AS_FINALLY, _AS_EXCEPT;
251 	static const string AS_PUBLIC, AS_PROTECTED, AS_PRIVATE;
252 	static const string AS_CLASS, AS_STRUCT, AS_UNION, AS_INTERFACE, AS_NAMESPACE;
253 	static const string AS_MODULE;
254 	static const string AS_END;
255 	static const string AS_SELECTOR;
256 	static const string AS_EXTERN, AS_ENUM;
257 	static const string AS_FINAL, AS_OVERRIDE;
258 	static const string AS_STATIC, AS_CONST, AS_SEALED, AS_VOLATILE, AS_NEW, AS_DELETE;
259 	static const string AS_NOEXCEPT, AS_INTERRUPT, AS_AUTORELEASEPOOL;
260 	static const string AS_WHERE, AS_LET, AS_SYNCHRONIZED;
261 	static const string AS_OPERATOR, AS_TEMPLATE;
262 	static const string AS_OPEN_BRACE, AS_CLOSE_BRACE;
263 	static const string AS_OPEN_LINE_COMMENT, AS_OPEN_COMMENT, AS_CLOSE_COMMENT;
264 	static const string AS_BAR_DEFINE, AS_BAR_INCLUDE, AS_BAR_IF, AS_BAR_EL, AS_BAR_ENDIF;
265 	static const string AS_AUTO, AS_RETURN;
266 	static const string AS_CIN, AS_COUT, AS_CERR;
267 	static const string AS_ASSIGN, AS_PLUS_ASSIGN, AS_MINUS_ASSIGN, AS_MULT_ASSIGN;
268 	static const string AS_DIV_ASSIGN, AS_MOD_ASSIGN, AS_XOR_ASSIGN, AS_OR_ASSIGN, AS_AND_ASSIGN;
269 	static const string AS_GR_GR_ASSIGN, AS_LS_LS_ASSIGN, AS_GR_GR_GR_ASSIGN, AS_LS_LS_LS_ASSIGN;
270 	static const string AS_GCC_MIN_ASSIGN, AS_GCC_MAX_ASSIGN;
271 	static const string AS_EQUAL, AS_PLUS_PLUS, AS_MINUS_MINUS, AS_NOT_EQUAL, AS_GR_EQUAL;
272 	static const string AS_LS_EQUAL, AS_LS_LS_LS, AS_LS_LS, AS_GR_GR_GR, AS_GR_GR;
273 	static const string AS_QUESTION_QUESTION, AS_LAMBDA;
274 	static const string AS_ARROW, AS_AND, AS_OR;
275 	static const string AS_SCOPE_RESOLUTION;
276 	static const string AS_PLUS, AS_MINUS, AS_MULT, AS_DIV, AS_MOD, AS_GR, AS_LS;
277 	static const string AS_NOT, AS_BIT_XOR, AS_BIT_OR, AS_BIT_AND, AS_BIT_NOT;
278 	static const string AS_QUESTION, AS_COLON, AS_SEMICOLON, AS_COMMA;
279 	static const string AS_ASM, AS__ASM__, AS_MS_ASM, AS_MS__ASM;
280 	static const string AS_QFOREACH, AS_QFOREVER, AS_FOREVER;
281 	static const string AS_FOREACH, AS_LOCK, AS_UNSAFE, AS_FIXED;
282 	static const string AS_GET, AS_SET, AS_ADD, AS_REMOVE;
283 	static const string AS_DELEGATE, AS_UNCHECKED;
284 	static const string AS_CONST_CAST, AS_DYNAMIC_CAST, AS_REINTERPRET_CAST, AS_STATIC_CAST;
285 	static const string AS_NS_DURING, AS_NS_HANDLER;
286 };  // Class ASResource
287 
288 //-----------------------------------------------------------------------------
289 // Class ASBase
290 // Functions definitions are at the end of ASResource.cpp.
291 //-----------------------------------------------------------------------------
292 
293 class ASBase : protected ASResource
294 {
295 private:
296 	// all variables should be set by the "init" function
297 	int baseFileType;      // a value from enum FileType
298 
299 protected:
ASBase()300 	ASBase() : baseFileType(C_TYPE) { }
301 
302 protected:  // inline functions
init(int fileTypeArg)303 	void init(int fileTypeArg) { baseFileType = fileTypeArg; }
isCStyle()304 	bool isCStyle() const { return (baseFileType == C_TYPE); }
isJavaStyle()305 	bool isJavaStyle() const { return (baseFileType == JAVA_TYPE); }
isSharpStyle()306 	bool isSharpStyle() const { return (baseFileType == SHARP_TYPE); }
isWhiteSpace(char ch)307 	bool isWhiteSpace(char ch) const { return (ch == ' ' || ch == '\t'); }
308 
309 protected:  // functions definitions are at the end of ASResource.cpp
310 	const string* findHeader(const string& line, int i,
311 	                         const vector<const string*>* possibleHeaders) const;
312 	bool findKeyword(const string& line, int i, const string& keyword) const;
313 	const string* findOperator(const string& line, int i,
314 	                           const vector<const string*>* possibleOperators) const;
315 	string getCurrentWord(const string& line, size_t index) const;
316 	bool isDigit(char ch) const;
317 	bool isLegalNameChar(char ch) const;
318 	bool isCharPotentialHeader(const string& line, size_t i) const;
319 	bool isCharPotentialOperator(char ch) const;
320 	bool isDigitSeparator(const string& line, int i) const;
321 	char peekNextChar(const string& line, int i) const;
322 
323 };  // Class ASBase
324 
325 //-----------------------------------------------------------------------------
326 // Class ASBeautifier
327 //-----------------------------------------------------------------------------
328 
329 class ASBeautifier : protected ASBase
330 {
331 public:
332 	ASBeautifier();
333 	virtual ~ASBeautifier();
334 	virtual void init(ASSourceIterator* iter);
335 	virtual string beautify(const string& originalLine);
336 	void setCaseIndent(bool state);
337 	void setClassIndent(bool state);
338 	void setContinuationIndentation(int indent = 1);
339 	void setCStyle();
340 	void setDefaultTabLength();
341 	void setEmptyLineFill(bool state);
342 	void setForceTabXIndentation(int length);
343 	void setAfterParenIndent(bool state);
344 	void setJavaStyle();
345 	void setLabelIndent(bool state);
346 	void setMaxContinuationIndentLength(int max);
347 	void setMaxInStatementIndentLength(int max);
348 	void setMinConditionalIndentOption(int min);
349 	void setMinConditionalIndentLength();
350 	void setModeManuallySet(bool state);
351 	void setModifierIndent(bool state);
352 	void setNamespaceIndent(bool state);
353 	void setAlignMethodColon(bool state);
354 	void setSharpStyle();
355 	void setSpaceIndentation(int length = 4);
356 	void setSwitchIndent(bool state);
357 	void setTabIndentation(int length = 4, bool forceTabs = false);
358 	void setPreprocDefineIndent(bool state);
359 	void setPreprocConditionalIndent(bool state);
360 	int  getBeautifierFileType() const;
361 	int  getFileType() const;
362 	int  getIndentLength() const;
363 	int  getTabLength() const;
364 	string getIndentString() const;
365 	string getNextWord(const string& line, size_t currPos) const;
366 	bool getAlignMethodColon() const;
367 	bool getBraceIndent() const;
368 	bool getBlockIndent() const;
369 	bool getCaseIndent() const;
370 	bool getClassIndent() const;
371 	bool getEmptyLineFill() const;
372 	bool getForceTabIndentation() const;
373 	bool getModeManuallySet() const;
374 	bool getModifierIndent() const;
375 	bool getNamespaceIndent() const;
376 	bool getPreprocDefineIndent() const;
377 	bool getSwitchIndent() const;
378 
379 protected:
380 	void deleteBeautifierVectors();
381 	int  getNextProgramCharDistance(const string& line, int i) const;
382 	int  indexOf(const vector<const string*>& container, const string* element) const;
383 	void setBlockIndent(bool state);
384 	void setBraceIndent(bool state);
385 	void setBraceIndentVtk(bool state);
386 	string extractPreprocessorStatement(const string& line) const;
387 	string trim(const string& str) const;
388 	string rtrim(const string& str) const;
389 
390 	// variables set by ASFormatter - must be updated in activeBeautifierStack
391 	int  inLineNumber;
392 	int  runInIndentContinuation;
393 	int  nonInStatementBrace;
394 	int  objCColonAlignSubsequent;		// for subsequent lines not counting indent
395 	bool lineCommentNoBeautify;
396 	bool isElseHeaderIndent;
397 	bool isCaseHeaderCommentIndent;
398 	bool isNonInStatementArray;
399 	bool isSharpAccessor;
400 	bool isSharpDelegate;
401 	bool isInExternC;
402 	bool isInBeautifySQL;
403 	bool isInIndentableStruct;
404 	bool isInIndentablePreproc;
405 
406 private:  // functions
407 	ASBeautifier(const ASBeautifier& other);     // inline functions
408 	ASBeautifier& operator=(ASBeautifier&);      // not to be implemented
409 
410 	void adjustObjCMethodDefinitionIndentation(const string& line_);
411 	void adjustObjCMethodCallIndentation(const string& line_);
412 	void adjustParsedLineIndentation(size_t iPrelim, bool isInExtraHeaderIndent);
413 	void computePreliminaryIndentation();
414 	void parseCurrentLine(const string& line);
415 	void popLastContinuationIndent();
416 	void processPreprocessor(const string& preproc, const string& line);
417 	void registerContinuationIndent(const string& line, int i, int spaceIndentCount_,
418 	                                int tabIncrementIn, int minIndent, bool updateParenStack);
419 	void registerContinuationIndentColon(const string& line, int i, int tabIncrementIn);
420 	void initVectors();
421 	void initTempStacksContainer(vector<vector<const string*>*>*& container,
422 	                             vector<vector<const string*>*>* value);
423 	void clearObjCMethodDefinitionAlignment();
424 	void deleteBeautifierContainer(vector<ASBeautifier*>*& container);
425 	void deleteTempStacksContainer(vector<vector<const string*>*>*& container);
426 	int  adjustIndentCountForBreakElseIfComments() const;
427 	int  computeObjCColonAlignment(const string& line, int colonAlignPosition) const;
428 	int  convertTabToSpaces(int i, int tabIncrementIn) const;
429 	int  getContinuationIndentAssign(const string& line, size_t currPos) const;
430 	int  getContinuationIndentComma(const string& line, size_t currPos) const;
431 	int  getObjCFollowingKeyword(const string& line, int bracePos) const;
432 	bool isIndentedPreprocessor(const string& line, size_t currPos) const;
433 	bool isLineEndComment(const string& line, int startPos) const;
434 	bool isPreprocessorConditionalCplusplus(const string& line) const;
435 	bool isInPreprocessorUnterminatedComment(const string& line);
436 	bool statementEndsWithComma(const string& line, int index) const;
437 	const string& getIndentedLineReturn(const string& newLine, const string& originalLine) const;
438 	string getIndentedSpaceEquivalent(const string& line_) const;
439 	string preLineWS(int lineIndentCount, int lineSpaceIndentCount) const;
440 	template<typename T> void deleteContainer(T& container);
441 	template<typename T> void initContainer(T& container, T value);
442 	vector<vector<const string*>*>* copyTempStacks(const ASBeautifier& other) const;
443 	pair<int, int> computePreprocessorIndent();
444 
445 private:  // variables
446 	int beautifierFileType;
447 	vector<const string*>* headers;
448 	vector<const string*>* nonParenHeaders;
449 	vector<const string*>* preBlockStatements;
450 	vector<const string*>* preCommandHeaders;
451 	vector<const string*>* assignmentOperators;
452 	vector<const string*>* nonAssignmentOperators;
453 	vector<const string*>* indentableHeaders;
454 
455 	vector<ASBeautifier*>* waitingBeautifierStack;
456 	vector<ASBeautifier*>* activeBeautifierStack;
457 	vector<int>* waitingBeautifierStackLengthStack;
458 	vector<int>* activeBeautifierStackLengthStack;
459 	vector<const string*>* headerStack;
460 	vector<vector<const string*>* >* tempStacks;
461 	vector<int>* squareBracketDepthStack;
462 	vector<bool>* blockStatementStack;
463 	vector<bool>* parenStatementStack;
464 	vector<bool>* braceBlockStateStack;
465 	vector<int>* continuationIndentStack;
466 	vector<int>* continuationIndentStackSizeStack;
467 	vector<int>* parenIndentStack;
468 	vector<pair<int, int> >* preprocIndentStack;
469 
470 	ASSourceIterator* sourceIterator;
471 	const string* currentHeader;
472 	const string* previousLastLineHeader;
473 	const string* probationHeader;
474 	const string* lastLineHeader;
475 	string indentString;
476 	string verbatimDelimiter;
477 	bool isInQuote;
478 	bool isInVerbatimQuote;
479 	bool haveLineContinuationChar;
480 	bool isInAsm;
481 	bool isInAsmOneLine;
482 	bool isInAsmBlock;
483 	bool isInComment;
484 	bool isInPreprocessorComment;
485 	bool isInRunInComment;
486 	bool isInCase;
487 	bool isInQuestion;
488 	bool isContinuation;
489 	bool isInHeader;
490 	bool isInTemplate;
491 	bool isInDefine;
492 	bool isInDefineDefinition;
493 	bool classIndent;
494 	bool isIndentModeOff;
495 	bool isInClassHeader;			// is in a class before the opening brace
496 	bool isInClassHeaderTab;		// is in an indentable class header line
497 	bool isInClassInitializer;		// is in a class after the ':' initializer
498 	bool isInClass;					// is in a class after the opening brace
499 	bool isInObjCMethodDefinition;
500 	bool isInObjCMethodCall;
501 	bool isInObjCMethodCallFirst;
502 	bool isImmediatelyPostObjCMethodDefinition;
503 	bool isImmediatelyPostObjCMethodCall;
504 	bool isInIndentablePreprocBlock;
505 	bool isInObjCInterface;
506 	bool isInEnum;
507 	bool isInEnumTypeID;
508 	bool isInLet;
509 	bool modifierIndent;
510 	bool switchIndent;
511 	bool caseIndent;
512 	bool namespaceIndent;
513 	bool blockIndent;
514 	bool braceIndent;
515 	bool braceIndentVtk;
516 	bool shouldIndentAfterParen;
517 	bool labelIndent;
518 	bool shouldIndentPreprocDefine;
519 	bool isInConditional;
520 	bool isModeManuallySet;
521 	bool shouldForceTabIndentation;
522 	bool emptyLineFill;
523 	bool backslashEndsPrevLine;
524 	bool lineOpensWithLineComment;
525 	bool lineOpensWithComment;
526 	bool lineStartsInComment;
527 	bool blockCommentNoIndent;
528 	bool blockCommentNoBeautify;
529 	bool previousLineProbationTab;
530 	bool lineBeginsWithOpenBrace;
531 	bool lineBeginsWithCloseBrace;
532 	bool lineBeginsWithComma;
533 	bool lineIsCommentOnly;
534 	bool lineIsLineCommentOnly;
535 	bool shouldIndentBracedLine;
536 	bool isInSwitch;
537 	bool foundPreCommandHeader;
538 	bool foundPreCommandMacro;
539 	bool shouldAlignMethodColon;
540 	bool shouldIndentPreprocConditional;
541 	int  indentCount;
542 	int  spaceIndentCount;
543 	int  spaceIndentObjCMethodAlignment;
544 	int  bracePosObjCMethodAlignment;
545 	int  colonIndentObjCMethodAlignment;
546 	int  lineOpeningBlocksNum;
547 	int  lineClosingBlocksNum;
548 	int  fileType;
549 	int  minConditionalOption;
550 	int  minConditionalIndent;
551 	int  parenDepth;
552 	int  indentLength;
553 	int  tabLength;
554 	int  continuationIndent;
555 	int  blockTabCount;
556 	int  maxContinuationIndent;
557 	int  classInitializerIndents;
558 	int  templateDepth;
559 	int  squareBracketCount;
560 	int  prevFinalLineSpaceIndentCount;
561 	int  prevFinalLineIndentCount;
562 	int  defineIndentCount;
563 	int  preprocBlockIndent;
564 	char quoteChar;
565 	char prevNonSpaceCh;
566 	char currentNonSpaceCh;
567 	char currentNonLegalCh;
568 	char prevNonLegalCh;
569 };  // Class ASBeautifier
570 
571 //-----------------------------------------------------------------------------
572 // Class ASEnhancer
573 //-----------------------------------------------------------------------------
574 
575 class ASEnhancer : protected ASBase
576 {
577 public:  // functions
578 	ASEnhancer();
579 	virtual ~ASEnhancer();
580 	void init(int, int, int, bool, bool, bool, bool, bool, bool, bool,
581 	          vector<const pair<const string, const string>* >*);
582 	void enhance(string& line, bool isInNamespace, bool isInPreprocessor, bool isInSQL);
583 
584 private:  // functions
585 	void   convertForceTabIndentToSpaces(string&  line) const;
586 	void   convertSpaceIndentToForceTab(string& line) const;
587 	size_t findCaseColon(const string&  line, size_t caseIndex) const;
588 	int    indentLine(string&  line, int indent) const;
589 	bool   isBeginDeclareSectionSQL(const string&  line, size_t index) const;
590 	bool   isEndDeclareSectionSQL(const string&  line, size_t index) const;
591 	bool   isOneLineBlockReached(const string& line, int startChar) const;
592 	void   parseCurrentLine(string& line, bool isInPreprocessor, bool isInSQL);
593 	size_t processSwitchBlock(string&  line, size_t index);
594 	int    unindentLine(string&  line, int unindent) const;
595 
596 private:
597 	// options from command line or options file
598 	int  indentLength;
599 	int  tabLength;
600 	bool useTabs;
601 	bool forceTab;
602 	bool namespaceIndent;
603 	bool caseIndent;
604 	bool preprocBlockIndent;
605 	bool preprocDefineIndent;
606 	bool emptyLineFill;
607 
608 	// parsing variables
609 	int  lineNumber;
610 	bool isInQuote;
611 	bool isInComment;
612 	char quoteChar;
613 
614 	// unindent variables
615 	int  braceCount;
616 	int  switchDepth;
617 	int  eventPreprocDepth;
618 	bool lookingForCaseBrace;
619 	bool unindentNextLine;
620 	bool shouldUnindentLine;
621 	bool shouldUnindentComment;
622 
623 	// struct used by ParseFormattedLine function
624 	// contains variables used to unindent the case blocks
625 	struct SwitchVariables
626 	{
627 		int  switchBraceCount;
628 		int  unindentDepth;
629 		bool unindentCase;
630 	};
631 
632 	SwitchVariables sw;                      // switch variables struct
633 	vector<SwitchVariables> switchStack;     // stack vector of switch variables
634 
635 	// event table variables
636 	bool nextLineIsEventIndent;             // begin event table indent is reached
637 	bool isInEventTable;                    // need to indent an event table
638 	vector<const pair<const string, const string>* >* indentableMacros;
639 
640 	// SQL variables
641 	bool nextLineIsDeclareIndent;           // begin declare section indent is reached
642 	bool isInDeclareSection;                // need to indent a declare section
643 
644 };  // Class ASEnhancer
645 
646 //-----------------------------------------------------------------------------
647 // Class ASFormatter
648 //-----------------------------------------------------------------------------
649 
650 class ASFormatter : public ASBeautifier
651 {
652 public:	// functions
653 	ASFormatter();
654 	virtual ~ASFormatter();
655 	virtual void init(ASSourceIterator* si);
656 	virtual bool hasMoreLines() const;
657 	virtual string nextLine();
658 	LineEndFormat getLineEndFormat() const;
659 	bool getIsLineReady() const;
660 	void setFormattingStyle(FormatStyle style);
661 	void setAddBracesMode(bool state);
662 	void setAddOneLineBracesMode(bool state);
663 	void setRemoveBracesMode(bool state);
664 	void setAttachClass(bool state);
665 	void setAttachClosingWhile(bool state);
666 	void setAttachExternC(bool state);
667 	void setAttachNamespace(bool state);
668 	void setAttachInline(bool state);
669 	void setBraceFormatMode(BraceMode mode);
670 	void setBreakAfterMode(bool state);
671 	void setBreakClosingHeaderBracesMode(bool state);
672 	void setBreakBlocksMode(bool state);
673 	void setBreakClosingHeaderBlocksMode(bool state);
674 	void setBreakElseIfsMode(bool state);
675 	void setBreakOneLineBlocksMode(bool state);
676 	void setBreakOneLineHeadersMode(bool state);
677 	void setBreakOneLineStatementsMode(bool state);
678 	void setMethodPrefixPaddingMode(bool state);
679 	void setMethodPrefixUnPaddingMode(bool state);
680 	void setReturnTypePaddingMode(bool state);
681 	void setReturnTypeUnPaddingMode(bool state);
682 	void setParamTypePaddingMode(bool state);
683 	void setParamTypeUnPaddingMode(bool state);
684 	void setCloseTemplatesMode(bool state);
685 	void setCommaPaddingMode(bool state);
686 	void setDeleteEmptyLinesMode(bool state);
687 	void setIndentCol1CommentsMode(bool state);
688 	void setLineEndFormat(LineEndFormat fmt);
689 	void setMaxCodeLength(int max);
690 	void setObjCColonPaddingMode(ObjCColonPad mode);
691 	void setOperatorPaddingMode(bool state);
692 	void setParensOutsidePaddingMode(bool state);
693 	void setParensFirstPaddingMode(bool state);
694 	void setParensInsidePaddingMode(bool state);
695 	void setParensHeaderPaddingMode(bool state);
696 	void setParensUnPaddingMode(bool state);
697 	void setPointerAlignment(PointerAlign alignment);
698 	void setPreprocBlockIndent(bool state);
699 	void setReferenceAlignment(ReferenceAlign alignment);
700 	void setStripCommentPrefix(bool state);
701 	void setTabSpaceConversionMode(bool state);
702 	size_t getChecksumIn() const;
703 	size_t getChecksumOut() const;
704 	int  getChecksumDiff() const;
705 	int  getFormatterFileType() const;
706 	// retained for compatability with release 2.06
707 	// "Brackets" have been changed to "Braces" in 3.0
708 	// they are referenced only by the old "bracket" options
709 	void setAddBracketsMode(bool state);
710 	void setAddOneLineBracketsMode(bool state);
711 	void setRemoveBracketsMode(bool state);
712 	void setBreakClosingHeaderBracketsMode(bool state);
713 
714 
715 private:  // functions
716 	ASFormatter(const ASFormatter& copy);       // not to be implemented
717 	ASFormatter& operator=(ASFormatter&);       // not to be implemented
718 	template<typename T> void deleteContainer(T& container);
719 	template<typename T> void initContainer(T& container, T value);
720 	char peekNextChar() const;
721 	BraceType getBraceType();
722 	bool adjustChecksumIn(int adjustment);
723 	bool computeChecksumIn(const string& currentLine_);
724 	bool computeChecksumOut(const string& beautifiedLine);
725 	bool addBracesToStatement();
726 	bool removeBracesFromStatement();
727 	bool commentAndHeaderFollows();
728 	bool getNextChar();
729 	bool getNextLine(bool emptyLineWasDeleted = false);
730 	bool isArrayOperator() const;
731 	bool isBeforeComment() const;
732 	bool isBeforeAnyComment() const;
733 	bool isBeforeAnyLineEndComment(int startPos) const;
734 	bool isBeforeMultipleLineEndComments(int startPos) const;
735 	bool isBraceType(BraceType a, BraceType b) const;
736 	bool isClassInitializer() const;
737 	bool isClosingHeader(const string* header) const;
738 	bool isCurrentBraceBroken() const;
739 	bool isDereferenceOrAddressOf() const;
740 	bool isExecSQL(const string& line, size_t index) const;
741 	bool isEmptyLine(const string& line) const;
742 	bool isExternC() const;
743 	bool isMultiStatementLine() const;
744 	bool isNextWordSharpNonParenHeader(int startChar) const;
745 	bool isNonInStatementArrayBrace() const;
746 	bool isOkToSplitFormattedLine();
747 	bool isPointerOrReference() const;
748 	bool isPointerOrReferenceCentered() const;
749 	bool isPointerOrReferenceVariable(const string& word) const;
750 	bool isSharpStyleWithParen(const string* header) const;
751 	bool isStructAccessModified(const string& firstLine, size_t index) const;
752 	bool isIndentablePreprocessorBlock(const string& firstLine, size_t index);
753 	bool isNDefPreprocStatement(const string& nextLine_, const string& preproc) const;
754 	bool isUnaryOperator() const;
755 	bool isUniformInitializerBrace() const;
756 	bool isImmediatelyPostCast() const;
757 	bool isInExponent() const;
758 	bool isInSwitchStatement() const;
759 	bool isNextCharOpeningBrace(int startChar) const;
760 	bool isOkToBreakBlock(BraceType braceType) const;
761 	bool isOperatorPaddingDisabled() const;
762 	bool pointerSymbolFollows() const;
763 	int  findObjCColonAlignment() const;
764 	int  getCurrentLineCommentAdjustment();
765 	int  getNextLineCommentAdjustment();
766 	int  isOneLineBlockReached(const string& line, int startChar) const;
767 	void adjustComments();
768 	void appendChar(char ch, bool canBreakLine);
769 	void appendCharInsideComments();
770 	void appendClosingHeader();
771 	void appendOperator(const string& sequence, bool canBreakLine = true);
772 	void appendSequence(const string& sequence, bool canBreakLine = true);
773 	void appendSpacePad();
774 	void appendSpaceAfter();
775 	void breakLine(bool isSplitLine = false);
776 	void buildLanguageVectors();
777 	void updateFormattedLineSplitPoints(char appendedChar);
778 	void updateFormattedLineSplitPointsOperator(const string& sequence);
779 	void checkIfTemplateOpener();
780 	void clearFormattedLineSplitPoints();
781 	void convertTabToSpaces();
782 	void deleteContainer(vector<BraceType>*& container);
783 	void formatArrayRunIn();
784 	void formatRunIn();
785 	void formatArrayBraces(BraceType braceType, bool isOpeningArrayBrace);
786 	void formatClosingBrace(BraceType braceType);
787 	void formatCommentBody();
788 	void formatCommentOpener();
789 	void formatCommentCloser();
790 	void formatLineCommentBody();
791 	void formatLineCommentOpener();
792 	void formatOpeningBrace(BraceType braceType);
793 	void formatQuoteBody();
794 	void formatQuoteOpener();
795 	void formatPointerOrReference();
796 	void formatPointerOrReferenceCast();
797 	void formatPointerOrReferenceToMiddle();
798 	void formatPointerOrReferenceToName();
799 	void formatPointerOrReferenceToType();
800 	void fixOptionVariableConflicts();
801 	void goForward(int i);
802 	void isLineBreakBeforeClosingHeader();
803 	void initContainer(vector<BraceType>*& container, vector<BraceType>* value);
804 	void initNewLine();
805 	void padObjCMethodColon();
806 	void padObjCMethodPrefix();
807 	void padObjCParamType();
808 	void padObjCReturnType();
809 	void padOperators(const string* newOperator);
810 	void padParens();
811 	void processPreprocessor();
812 	void resetEndOfStatement();
813 	void setAttachClosingBraceMode(bool state);
814 	void stripCommentPrefix();
815 	void testForTimeToSplitFormattedLine();
816 	void trimContinuationLine();
817 	void updateFormattedLineSplitPointsPointerOrReference(size_t index);
818 	size_t findFormattedLineSplitPoint() const;
819 	size_t findNextChar(const string& line, char searchChar, int searchStart = 0) const;
820 	const string* checkForHeaderFollowingComment(const string& firstLine) const;
821 	const string* getFollowingOperator() const;
822 	string getPreviousWord(const string& line, int currPos) const;
823 	string peekNextText(const string& firstLine,
824 	                    bool endOnEmptyLine = false,
825 	                    shared_ptr<ASPeekStream> streamArg = nullptr) const;
826 
827 private:  // variables
828 	int formatterFileType;
829 	vector<const string*>* headers;
830 	vector<const string*>* nonParenHeaders;
831 	vector<const string*>* preDefinitionHeaders;
832 	vector<const string*>* preCommandHeaders;
833 	vector<const string*>* operators;
834 	vector<const string*>* assignmentOperators;
835 	vector<const string*>* castOperators;
836 	vector<const pair<const string, const string>* >* indentableMacros;	// for ASEnhancer
837 
838 	ASSourceIterator* sourceIterator;
839 	ASEnhancer* enhancer;
840 
841 	vector<const string*>* preBraceHeaderStack;
842 	vector<BraceType>* braceTypeStack;
843 	vector<int>* parenStack;
844 	vector<bool>* structStack;
845 	vector<bool>* questionMarkStack;
846 
847 	string currentLine;
848 	string formattedLine;
849 	string readyFormattedLine;
850 	string verbatimDelimiter;
851 	const string* currentHeader;
852 	char currentChar;
853 	char previousChar;
854 	char previousNonWSChar;
855 	char previousCommandChar;
856 	char quoteChar;
857 	streamoff preprocBlockEnd;
858 	int  charNum;
859 	int  runInIndentChars;
860 	int  nextLineSpacePadNum;
861 	int  objCColonAlign;
862 	int  preprocBraceTypeStackSize;
863 	int  spacePadNum;
864 	int  tabIncrementIn;
865 	int  templateDepth;
866 	int  squareBracketCount;
867 	size_t checksumIn;
868 	size_t checksumOut;
869 	size_t currentLineFirstBraceNum;	// first brace location on currentLine
870 	size_t formattedLineCommentNum;     // comment location on formattedLine
871 	size_t leadingSpaces;
872 	size_t maxCodeLength;
873 
874 	// possible split points
875 	size_t maxSemi;			// probably a 'for' statement
876 	size_t maxAndOr;		// probably an 'if' statement
877 	size_t maxComma;
878 	size_t maxParen;
879 	size_t maxWhiteSpace;
880 	size_t maxSemiPending;
881 	size_t maxAndOrPending;
882 	size_t maxCommaPending;
883 	size_t maxParenPending;
884 	size_t maxWhiteSpacePending;
885 
886 	size_t previousReadyFormattedLineLength;
887 	FormatStyle formattingStyle;
888 	BraceMode braceFormatMode;
889 	BraceType previousBraceType;
890 	PointerAlign pointerAlignment;
891 	ReferenceAlign referenceAlignment;
892 	ObjCColonPad objCColonPadMode;
893 	LineEndFormat lineEnd;
894 	bool isVirgin;
895 	bool isInVirginLine;
896 	bool shouldPadCommas;
897 	bool shouldPadOperators;
898 	bool shouldPadParensOutside;
899 	bool shouldPadFirstParen;
900 	bool shouldPadParensInside;
901 	bool shouldPadHeader;
902 	bool shouldStripCommentPrefix;
903 	bool shouldUnPadParens;
904 	bool shouldConvertTabs;
905 	bool shouldIndentCol1Comments;
906 	bool shouldIndentPreprocBlock;
907 	bool shouldCloseTemplates;
908 	bool shouldAttachExternC;
909 	bool shouldAttachNamespace;
910 	bool shouldAttachClass;
911 	bool shouldAttachClosingWhile;
912 	bool shouldAttachInline;
913 	bool isInLineComment;
914 	bool isInComment;
915 	bool isInCommentStartLine;
916 	bool noTrimCommentContinuation;
917 	bool isInPreprocessor;
918 	bool isInPreprocessorBeautify;
919 	bool isInTemplate;
920 	bool doesLineStartComment;
921 	bool lineEndsInCommentOnly;
922 	bool lineIsCommentOnly;
923 	bool lineIsLineCommentOnly;
924 	bool lineIsEmpty;
925 	bool isImmediatelyPostCommentOnly;
926 	bool isImmediatelyPostEmptyLine;
927 	bool isInClassInitializer;
928 	bool isInQuote;
929 	bool isInVerbatimQuote;
930 	bool haveLineContinuationChar;
931 	bool isInQuoteContinuation;
932 	bool isHeaderInMultiStatementLine;
933 	bool isSpecialChar;
934 	bool isNonParenHeader;
935 	bool foundQuestionMark;
936 	bool foundPreDefinitionHeader;
937 	bool foundNamespaceHeader;
938 	bool foundClassHeader;
939 	bool foundStructHeader;
940 	bool foundInterfaceHeader;
941 	bool foundPreCommandHeader;
942 	bool foundPreCommandMacro;
943 	bool foundTrailingReturnType;
944 	bool foundCastOperator;
945 	bool isInLineBreak;
946 	bool endOfAsmReached;
947 	bool endOfCodeReached;
948 	bool lineCommentNoIndent;
949 	bool isFormattingModeOff;
950 	bool isInEnum;
951 	bool isInExecSQL;
952 	bool isInAsm;
953 	bool isInAsmOneLine;
954 	bool isInAsmBlock;
955 	bool isLineReady;
956 	bool elseHeaderFollowsComments;
957 	bool caseHeaderFollowsComments;
958 	bool isPreviousBraceBlockRelated;
959 	bool isInPotentialCalculation;
960 	bool isCharImmediatelyPostComment;
961 	bool isPreviousCharPostComment;
962 	bool isCharImmediatelyPostLineComment;
963 	bool isCharImmediatelyPostOpenBlock;
964 	bool isCharImmediatelyPostCloseBlock;
965 	bool isCharImmediatelyPostTemplate;
966 	bool isCharImmediatelyPostReturn;
967 	bool isCharImmediatelyPostThrow;
968 	bool isCharImmediatelyPostNewDelete;
969 	bool isCharImmediatelyPostOperator;
970 	bool isCharImmediatelyPostPointerOrReference;
971 	bool isInObjCMethodDefinition;
972 	bool isInObjCInterface;
973 	bool isInObjCReturnType;
974 	bool isInObjCSelector;
975 	bool breakCurrentOneLineBlock;
976 	bool shouldRemoveNextClosingBrace;
977 	bool isInBraceRunIn;
978 	bool currentLineBeginsWithBrace;
979 	bool attachClosingBraceMode;
980 	bool shouldBreakOneLineBlocks;
981 	bool shouldBreakOneLineHeaders;
982 	bool shouldBreakOneLineStatements;
983 	bool shouldBreakClosingHeaderBraces;
984 	bool shouldBreakElseIfs;
985 	bool shouldBreakLineAfterLogical;
986 	bool shouldAddBraces;
987 	bool shouldAddOneLineBraces;
988 	bool shouldRemoveBraces;
989 	bool shouldPadMethodColon;
990 	bool shouldPadMethodPrefix;
991 	bool shouldReparseCurrentChar;
992 	bool shouldUnPadMethodPrefix;
993 	bool shouldPadReturnType;
994 	bool shouldUnPadReturnType;
995 	bool shouldPadParamType;
996 	bool shouldUnPadParamType;
997 	bool shouldDeleteEmptyLines;
998 	bool needHeaderOpeningBrace;
999 	bool shouldBreakLineAtNextChar;
1000 	bool shouldKeepLineUnbroken;
1001 	bool passedSemicolon;
1002 	bool passedColon;
1003 	bool isImmediatelyPostNonInStmt;
1004 	bool isCharImmediatelyPostNonInStmt;
1005 	bool isImmediatelyPostComment;
1006 	bool isImmediatelyPostLineComment;
1007 	bool isImmediatelyPostEmptyBlock;
1008 	bool isImmediatelyPostObjCMethodPrefix;
1009 	bool isImmediatelyPostPreprocessor;
1010 	bool isImmediatelyPostReturn;
1011 	bool isImmediatelyPostThrow;
1012 	bool isImmediatelyPostNewDelete;
1013 	bool isImmediatelyPostOperator;
1014 	bool isImmediatelyPostTemplate;
1015 	bool isImmediatelyPostPointerOrReference;
1016 	bool shouldBreakBlocks;
1017 	bool shouldBreakClosingHeaderBlocks;
1018 	bool isPrependPostBlockEmptyLineRequested;
1019 	bool isAppendPostBlockEmptyLineRequested;
1020 	bool isIndentableProprocessor;
1021 	bool isIndentableProprocessorBlock;
1022 	bool prependEmptyLine;
1023 	bool appendOpeningBrace;
1024 	bool foundClosingHeader;
1025 	bool isInHeader;
1026 	bool isImmediatelyPostHeader;
1027 	bool isInCase;
1028 	bool isFirstPreprocConditional;
1029 	bool processedFirstConditional;
1030 	bool isJavaStaticConstructor;
1031 
1032 private:  // inline functions
1033 	// append the CURRENT character (curentChar) to the current formatted line.
1034 	void appendCurrentChar(bool canBreakLine = true)
1035 	{ appendChar(currentChar, canBreakLine); }
1036 
1037 	// check if a specific sequence exists in the current placement of the current line
isSequenceReached(const char * sequence)1038 	bool isSequenceReached(const char* sequence) const
1039 	{ return currentLine.compare(charNum, strlen(sequence), sequence) == 0; }
1040 
1041 	// call ASBase::findHeader for the current character
findHeader(const vector<const string * > * headers_)1042 	const string* findHeader(const vector<const string*>* headers_)
1043 	{ return ASBase::findHeader(currentLine, charNum, headers_); }
1044 
1045 	// call ASBase::findOperator for the current character
findOperator(const vector<const string * > * operators_)1046 	const string* findOperator(const vector<const string*>* operators_)
1047 	{ return ASBase::findOperator(currentLine, charNum, operators_); }
1048 };  // Class ASFormatter
1049 
1050 //-----------------------------------------------------------------------------
1051 // astyle namespace global declarations
1052 //-----------------------------------------------------------------------------
1053 // sort comparison functions for ASResource
1054 bool sortOnLength(const string* a, const string* b);
1055 bool sortOnName(const string* a, const string* b);
1056 
1057 }   // namespace astyle
1058 
1059 // end of astyle namespace  --------------------------------------------------
1060 
1061 #endif // closes ASTYLE_H
1062