View | Details | Raw Unified | Return to bug 293300 | Differences between
and this patch

Collapse All | Expand All

(-)compiler/org/eclipse/jdt/internal/compiler/parser/Scanner.java (-24 / +14 lines)
Lines 3664-3699 Link Here
3664
	if (this.currentPosition <= 0)
3664
	if (this.currentPosition <= 0)
3665
		return "NOT started!\n\n"+ new String(this.source); //$NON-NLS-1$
3665
		return "NOT started!\n\n"+ new String(this.source); //$NON-NLS-1$
3666
3666
3667
	char front[] = new char[this.startPosition];
3667
	StringBuffer buffer = new StringBuffer();
3668
	System.arraycopy(this.source, 0, front, 0, this.startPosition);
3668
	if (this.startPosition < 1000) {
3669
		buffer.append(this.source, 0, this.startPosition);
3670
	} else {
3671
		buffer.append("<source beginning>\n...\n"); //$NON-NLS-1$
3672
		int line = Util.getLineNumber(this.startPosition-1000, this.lineEnds, 0, this.lineEnds.length);
3673
		int lineStart = getLineStart(line);
3674
		buffer.append(this.source, lineStart, this.startPosition-lineStart);
3675
	}
3669
3676
3677
	buffer.append("\n===============================\nStarts here -->"); //$NON-NLS-1$
3670
	int middleLength = (this.currentPosition - 1) - this.startPosition + 1;
3678
	int middleLength = (this.currentPosition - 1) - this.startPosition + 1;
3671
	char middle[];
3672
	if (middleLength > -1) {
3679
	if (middleLength > -1) {
3673
		middle = new char[middleLength];
3680
		buffer.append(this.source, this.startPosition, middleLength);
3674
		System.arraycopy(
3675
			this.source,
3676
			this.startPosition,
3677
			middle,
3678
			0,
3679
			middleLength);
3680
	} else {
3681
		middle = CharOperation.NO_CHAR;
3682
	}
3681
	}
3682
	buffer.append("<-- Ends here\n===============================\n"); //$NON-NLS-1$
3683
3683
3684
	char end[] = new char[this.eofPosition - (this.currentPosition - 1)];
3684
	buffer.append(this.source, (this.currentPosition - 1) + 1, this.eofPosition - (this.currentPosition - 1) - 1);
3685
	System.arraycopy(
3686
		this.source,
3687
		(this.currentPosition - 1) + 1,
3688
		end,
3689
		0,
3690
		this.eofPosition - (this.currentPosition - 1) - 1);
3691
3685
3692
	return new String(front)
3686
	return buffer.toString();
3693
		+ "\n===============================\nStarts here -->" //$NON-NLS-1$
3694
		+ new String(middle)
3695
		+ "<-- Ends here\n===============================\n" //$NON-NLS-1$
3696
		+ new String(end);
3697
}
3687
}
3698
public String toStringAction(int act) {
3688
public String toStringAction(int act) {
3699
	switch (act) {
3689
	switch (act) {
(-)formatter/org/eclipse/jdt/internal/formatter/CodeFormatterVisitor.java (-3 / +3 lines)
Lines 1868-1874 Link Here
1868
				this.scribe.indent();
1868
				this.scribe.indent();
1869
			}
1869
			}
1870
			this.scribe.printNextToken(TerminalTokens.TokenNameLBRACE, insertSpaceBeforeBrace);
1870
			this.scribe.printNextToken(TerminalTokens.TokenNameLBRACE, insertSpaceBeforeBrace);
1871
			this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.BASIC_TRAILING_COMMENT);
1871
			this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.UNMODIFIABLE_TRAILING_COMMENT);
1872
	}
1872
	}
1873
	private void formatStatements(BlockScope scope, final Statement[] statements, boolean insertNewLineAfterLastStatement) {
1873
	private void formatStatements(BlockScope scope, final Statement[] statements, boolean insertNewLineAfterLastStatement) {
1874
		int statementsLength = statements.length;
1874
		int statementsLength = statements.length;
Lines 4254-4260 Link Here
4254
		} else {
4254
		} else {
4255
			// no method body
4255
			// no method body
4256
			this.scribe.printNextToken(TerminalTokens.TokenNameSEMICOLON, this.preferences.insert_space_before_semicolon);
4256
			this.scribe.printNextToken(TerminalTokens.TokenNameSEMICOLON, this.preferences.insert_space_before_semicolon);
4257
			this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.BASIC_TRAILING_COMMENT);
4257
			this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.COMPLEX_TRAILING_COMMENT);
4258
		}
4258
		}
4259
		return false;
4259
		return false;
4260
	}
4260
	}
Lines 4951-4962 Link Here
4951
						this.scribe.unIndent();
4951
						this.scribe.unIndent();
4952
					}
4952
					}
4953
					statement.traverse(this, scope);
4953
					statement.traverse(this, scope);
4954
					this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.BASIC_TRAILING_COMMENT);
4955
					wasACase = true;
4954
					wasACase = true;
4956
					wasAStatement = false;
4955
					wasAStatement = false;
4957
					if (this.preferences.indent_switchstatements_compare_to_cases) {
4956
					if (this.preferences.indent_switchstatements_compare_to_cases) {
4958
						this.scribe.indent();
4957
						this.scribe.indent();
4959
					}
4958
					}
4959
					this.scribe.printComment(CodeFormatter.K_UNKNOWN, Scribe.COMPLEX_TRAILING_COMMENT);
4960
				} else if (statement instanceof BreakStatement) {
4960
				} else if (statement instanceof BreakStatement) {
4961
					if (this.preferences.indent_breaks_compare_to_cases) {
4961
					if (this.preferences.indent_breaks_compare_to_cases) {
4962
						if (wasAStatement && !this.preferences.indent_switchstatements_compare_to_cases) {
4962
						if (wasAStatement && !this.preferences.indent_switchstatements_compare_to_cases) {
(-)formatter/org/eclipse/jdt/internal/formatter/Location.java (-1 / +1 lines)
Lines 43-49 Link Here
43
		this.outputColumn = scribe.column;
43
		this.outputColumn = scribe.column;
44
		this.outputLine = scribe.line;
44
		this.outputLine = scribe.line;
45
		this.inputOffset = sourceRestart;
45
		this.inputOffset = sourceRestart;
46
		this.inputColumn = scribe.getCurrentIndentation(sourceRestart);
46
		this.inputColumn = scribe.getCurrentColumn(sourceRestart);
47
		this.outputIndentationLevel = scribe.indentationLevel;
47
		this.outputIndentationLevel = scribe.indentationLevel;
48
		this.lastNumberOfNewLines = scribe.lastNumberOfNewLines;
48
		this.lastNumberOfNewLines = scribe.lastNumberOfNewLines;
49
		this.needSpace = scribe.needSpace;
49
		this.needSpace = scribe.needSpace;
(-)formatter/org/eclipse/jdt/internal/formatter/Scribe.java (-45 / +194 lines)
Lines 106-117 Link Here
106
	private static final int INCLUDE_LINE_COMMENTS = CodeFormatter.F_INCLUDE_COMMENTS | CodeFormatter.K_SINGLE_LINE_COMMENT;
106
	private static final int INCLUDE_LINE_COMMENTS = CodeFormatter.F_INCLUDE_COMMENTS | CodeFormatter.K_SINGLE_LINE_COMMENT;
107
	private static final int SKIP_FIRST_WHITESPACE_TOKEN = -2;
107
	private static final int SKIP_FIRST_WHITESPACE_TOKEN = -2;
108
	private static final int INVALID_TOKEN = 2000;
108
	private static final int INVALID_TOKEN = 2000;
109
	static final int NO_TRAILING_COMMENT = 0;
109
	static final int NO_TRAILING_COMMENT = 0x0000;
110
	static final int BASIC_TRAILING_COMMENT = 1;
110
	static final int BASIC_TRAILING_COMMENT = 0x0100;
111
	static final int IMPORT_TRAILING_COMMENT = 2;
111
	static final int COMPLEX_TRAILING_COMMENT = 0x0200;
112
	static final int IMPORT_TRAILING_COMMENT = COMPLEX_TRAILING_COMMENT | 0x0001;
113
	static final int UNMODIFIABLE_TRAILING_COMMENT = 0x0400;
112
	private int formatComments = 0;
114
	private int formatComments = 0;
113
	private int headerEndPosition = -1;
115
	private int headerEndPosition = -1;
114
	String commentIndentation; // indentation requested in comments (usually in javadoc root tags description)
116
	String commentIndentation; // indentation requested in comments (usually in javadoc root tags description)
117
	// Class to store previous line comment information
118
	class LineComment {
119
		boolean contiguous = false;
120
		int currentColumn, indentation;
121
		int lines;
122
		char[] leadingSpaces;
123
	}
124
	final LineComment lastLineComment = new LineComment();
125
115
126
116
	// New way to format javadoc
127
	// New way to format javadoc
117
	private FormatterCommentParser formatterCommentParser; // specialized parser to format comments
128
	private FormatterCommentParser formatterCommentParser; // specialized parser to format comments
Lines 787-796 Link Here
787
		return null;
798
		return null;
788
	}
799
	}
789
800
790
	private int getCurrentCommentOffset(int start) {
801
	private int getCurrentCommentColumn(int start) {
791
		int linePtr = -Arrays.binarySearch(this.lineEnds, start);
802
		int linePtr = -Arrays.binarySearch(this.lineEnds, start);
792
		int offset = 0;
803
		int commentColumn = 1;
793
		int beginningOfLine = getLineEnd(linePtr - 1);
804
		int beginningOfLine = getLineEnd(linePtr - 1)+1;
794
		if (beginningOfLine == -1) {
805
		if (beginningOfLine == -1) {
795
			beginningOfLine = 0;
806
			beginningOfLine = 0;
796
		}
807
		}
Lines 800-834 Link Here
800
		// find the position of the beginning of the line containing the comment
811
		// find the position of the beginning of the line containing the comment
801
		while (beginningOfLine > currentStartPosition) {
812
		while (beginningOfLine > currentStartPosition) {
802
			if (linePtr > 0) {
813
			if (linePtr > 0) {
803
				beginningOfLine = getLineEnd(--linePtr);
814
				beginningOfLine = getLineEnd(--linePtr)+1;
804
			} else {
815
			} else {
805
				beginningOfLine = 0;
816
				beginningOfLine = 0;
806
				break;
817
				break;
807
			}
818
			}
808
		}
819
		}
809
		for (int i = currentStartPosition - 1; i >= beginningOfLine ; i--) {
820
		for (int i=beginningOfLine; i < currentStartPosition ; i++) {
810
			char currentCharacter = source[i];
821
			char currentCharacter = source[i];
811
			switch (currentCharacter) {
822
			switch (currentCharacter) {
812
				case '\t' :
823
				case '\t' :
813
					offset += this.tabLength;
824
					if (this.tabLength != 0) {
825
						int reminder = commentColumn % this.tabLength;
826
						if (reminder == 0) {
827
							commentColumn += this.tabLength;
828
						} else {
829
							commentColumn = ((commentColumn / this.tabLength) + 1) * this.tabLength + 1;
830
						}
831
					}
832
					break;
833
				case '\r' :
834
				case '\n' :
835
					commentColumn = 0;
836
					break;
837
				default:
838
					commentColumn++;
839
					break;
840
			}
841
		}
842
		return commentColumn;
843
	}
844
845
	int getCurrentColumn(char[] whitespaces) {
846
		int length = whitespaces.length;
847
		if (this.tabLength == 0) return length;
848
		int currentColumn = 1;
849
		for (int i=0; i<length; i++) {
850
			char ch = whitespaces[i];
851
			switch (ch) {
852
				case '\t' :
853
					int reminder = (currentColumn-1) % this.tabLength;
854
					if (reminder == 0) {
855
						currentColumn += this.tabLength;
856
					} else {
857
						currentColumn = ((currentColumn / this.tabLength) + 1) * this.tabLength + 1;
858
					}
814
					break;
859
					break;
815
				case '\r' :
860
				case '\r' :
816
				case '\n' :
861
				case '\n' :
862
					currentColumn = 0;
817
					break;
863
					break;
818
				default:
864
				default:
819
					offset++;
865
					currentColumn++;
820
					break;
866
					break;
821
			}
867
			}
822
		}
868
		}
823
		return offset;
869
		return currentColumn;
824
	}
870
	}
825
871
826
	int getCurrentIndentation(int start) {
872
	int getCurrentColumn(int start) {
827
		int linePtr = Arrays.binarySearch(this.lineEnds, start);
873
		int linePtr = Arrays.binarySearch(this.lineEnds, start);
828
		if (linePtr < 0) {
874
		if (linePtr < 0) {
829
			linePtr = -linePtr - 1;
875
			linePtr = -linePtr - 1;
830
		}
876
		}
831
		int offset = 0;
877
		int currentColumn = 1;
832
		int beginningOfLine = getLineEnd(linePtr)+1;
878
		int beginningOfLine = getLineEnd(linePtr)+1;
833
		if (beginningOfLine == -1) {
879
		if (beginningOfLine == -1) {
834
			beginningOfLine = 0;
880
			beginningOfLine = 0;
Lines 839-857 Link Here
839
			char currentCharacter = source[i];
885
			char currentCharacter = source[i];
840
			switch (currentCharacter) {
886
			switch (currentCharacter) {
841
				case '\t' :
887
				case '\t' :
842
					offset += this.tabLength;
888
					if (this.tabLength != 0) {
889
						int reminder = (currentColumn-1) % this.tabLength;
890
						if (reminder == 0) {
891
							currentColumn += this.tabLength;
892
						} else {
893
							currentColumn = ((currentColumn / this.tabLength) + 1) * this.tabLength + 1;
894
						}
895
					}
843
					break;
896
					break;
844
				case '\r' :
897
				case '\r' :
845
				case '\n' :
898
				case '\n' :
899
					currentColumn = 0;
846
					break;
900
					break;
847
				case ' ':
901
				case ' ':
848
					offset++;
902
					currentColumn++;
849
					break;
903
					break;
850
				default:
904
				default:
851
					return offset;
905
					return currentColumn;
852
			}
906
			}
853
		}
907
		}
854
		return offset;
908
		return currentColumn;
855
	}
909
	}
856
910
857
	public String getEmptyLines(int linesNumber) {
911
	public String getEmptyLines(int linesNumber) {
Lines 1009-1015 Link Here
1009
					StringBuffer buffer = new StringBuffer(getNewLine());
1063
					StringBuffer buffer = new StringBuffer(getNewLine());
1010
					
1064
					
1011
					// Look for current indentation
1065
					// Look for current indentation
1012
					int currentColumn = getCurrentIndentation(this.scanner.currentPosition);
1066
					int currentIndentation = getCurrentColumn(this.scanner.currentPosition) - 1;
1013
					
1067
					
1014
					// Determine whether the alignment indentation can be used or not
1068
					// Determine whether the alignment indentation can be used or not
1015
					// So far, the best algorithm is to use it when
1069
					// So far, the best algorithm is to use it when
Lines 1036-1049 Link Here
1036
					}
1090
					}
1037
					
1091
					
1038
					// Use the current indentation if over the computed indentation
1092
					// Use the current indentation if over the computed indentation
1039
					if (this.indentationLevel < currentColumn) {
1093
					if (this.indentationLevel < currentIndentation) {
1040
						this.indentationLevel = currentColumn;
1094
						this.indentationLevel = currentIndentation;
1041
					}
1095
					}
1042
					
1096
					
1043
					// Debug
1097
					// Debug
1044
					if (DefaultCodeFormatter.DEBUG) {
1098
					if (DefaultCodeFormatter.DEBUG) {
1045
						System.out.println(" - format brace = "+this.formatBrace); //$NON-NLS-1$
1099
						System.out.println(" - format brace = "+this.formatBrace); //$NON-NLS-1$
1046
						System.out.println(" - current column = "+currentColumn); //$NON-NLS-1$
1100
						System.out.println(" - current column = "+(currentIndentation+1)); //$NON-NLS-1$
1047
						System.out.println(" - current position = "+this.scanner.currentPosition); //$NON-NLS-1$
1101
						System.out.println(" - current position = "+this.scanner.currentPosition); //$NON-NLS-1$
1048
						System.out.print(" - current line = "); //$NON-NLS-1$
1102
						System.out.print(" - current line = "); //$NON-NLS-1$
1049
						int linePtr = Arrays.binarySearch(this.lineEnds, this.scanner.currentPosition);
1103
						int linePtr = Arrays.binarySearch(this.lineEnds, this.scanner.currentPosition);
Lines 1387-1393 Link Here
1387
		if ((commentColumn-1) > this.indentationLevel) {
1441
		if ((commentColumn-1) > this.indentationLevel) {
1388
			this.indentationLevel = commentColumn-1;
1442
			this.indentationLevel = commentColumn-1;
1389
		}
1443
		}
1390
		int currentCommentOffset = onFirstColumn ? 0 : getCurrentCommentOffset(start);
1444
		int currentCommentIndentation = onFirstColumn ? 0 : getCurrentCommentColumn(start) - 1;
1391
		boolean formatComment = (isJavadoc && (this.formatComments & CodeFormatter.K_JAVA_DOC) != 0) || (!isJavadoc && (this.formatComments & CodeFormatter.K_MULTI_LINE_COMMENT) != 0);
1445
		boolean formatComment = (isJavadoc && (this.formatComments & CodeFormatter.K_JAVA_DOC) != 0) || (!isJavadoc && (this.formatComments & CodeFormatter.K_MULTI_LINE_COMMENT) != 0);
1392
1446
1393
		try {
1447
		try {
Lines 1441-1459 Link Here
1441
							} else {
1495
							} else {
1442
								if (ScannerHelper.isWhitespace((char) currentCharacter)) {
1496
								if (ScannerHelper.isWhitespace((char) currentCharacter)) {
1443
									int previousStartPosition = this.scanner.currentPosition;
1497
									int previousStartPosition = this.scanner.currentPosition;
1444
									int count = 0;
1498
									int currentIndentation = 0;
1445
									loop: while(currentCharacter != -1 && currentCharacter != '\r' && currentCharacter != '\n' && ScannerHelper.isWhitespace((char) currentCharacter)) {
1499
									loop: while(currentCharacter != -1 && currentCharacter != '\r' && currentCharacter != '\n' && ScannerHelper.isWhitespace((char) currentCharacter)) {
1446
										if (count >= currentCommentOffset) {
1500
										if (currentIndentation >= currentCommentIndentation) {
1447
											break loop;
1501
											break loop;
1448
										}
1502
										}
1449
										previousStart = nextCharacterStart;
1503
										previousStart = nextCharacterStart;
1450
										previousStartPosition = this.scanner.currentPosition;
1504
										previousStartPosition = this.scanner.currentPosition;
1451
										switch(currentCharacter) {
1505
										switch(currentCharacter) {
1452
											case '\t' :
1506
											case '\t' :
1453
												count += this.tabLength;
1507
												if (this.tabLength != 0) {
1508
													int reminder = currentIndentation % this.tabLength;
1509
													if (reminder == 0) {
1510
														currentIndentation += this.tabLength;
1511
													} else {
1512
														currentIndentation = ((currentIndentation / this.tabLength) + 1) * this.tabLength;
1513
													}
1514
												}
1454
												break;
1515
												break;
1455
											default :
1516
											default :
1456
												count ++;
1517
												currentIndentation ++;
1457
										}
1518
										}
1458
										currentCharacter = this.scanner.getNextChar();
1519
										currentCharacter = this.scanner.getNextChar();
1459
										nextCharacterStart = this.scanner.currentPosition;
1520
										nextCharacterStart = this.scanner.currentPosition;
Lines 2108-2134 Link Here
2108
						// If following token is a line comment on the same line or the line just after,
2169
						// If following token is a line comment on the same line or the line just after,
2109
						// then it might be not really formatted as a trailing comment
2170
						// then it might be not really formatted as a trailing comment
2110
						boolean realTrailing = trailing > NO_TRAILING_COMMENT;
2171
						boolean realTrailing = trailing > NO_TRAILING_COMMENT;
2111
						if (trailing == IMPORT_TRAILING_COMMENT && this.scanner.currentCharacter == '/' && lines <= 1) {
2172
						if (realTrailing && this.scanner.currentCharacter == '/' && (lines == 0 || (lines == 1 && !hasLineComment && trailing == IMPORT_TRAILING_COMMENT))) {
2112
							int currentPosition = this.scanner.currentPosition;
2173
							// sometimes changing the trailing may not be the best idea
2113
							if (this.scanner.getNextToken() == TerminalTokens.TokenNameCOMMENT_LINE) {
2174
							// for complex trailing comment, it's basically a good idea
2114
								int token = this.scanner.getNextToken();
2175
							boolean canChangeTrailing = (trailing & COMPLEX_TRAILING_COMMENT) != 0;
2115
								while (token == TerminalTokens.TokenNameCOMMENT_LINE) {
2176
							// for basic trailing comment preceded by a line comment, then it depends on the comments relative position
2116
									token = this.scanner.getNextToken();
2177
							// when following comment column (after having been rounded) is below the preceding one,
2178
							// then it becomes not a good idea to change the trailing flag
2179
							if (trailing == BASIC_TRAILING_COMMENT && hasLineComment) {
2180
								int currentCommentColumn = getCurrentColumn(whiteSpaces);
2181
								int lastCommentColumn = this.lastLineComment.currentColumn;
2182
								if (this.tabLength > 0) {
2183
									if ((currentCommentColumn % this.tabLength) == 0) {
2184
										lastCommentColumn = (lastCommentColumn / this.tabLength) * this.tabLength;
2185
									} else {
2186
										currentCommentColumn = ((currentCommentColumn / this.tabLength) + 1) * this.tabLength;
2187
									}
2117
								}
2188
								}
2118
								if (token == TerminalTokens.TokenNameWHITESPACE) {
2189
								canChangeTrailing = currentCommentColumn >= lastCommentColumn;
2119
									char[] secondWhiteSpaces = this.scanner.getCurrentTokenSource();
2190
							}
2120
									loop: for (int i = 0, max = secondWhiteSpaces.length; i < max; i++) {
2191
							// if the trailing can be change, then look at the following tokens
2121
										switch(secondWhiteSpaces[i]) {
2192
							if (canChangeTrailing) {
2122
											case '\r' :
2193
								int currentPosition = this.scanner.currentPosition;
2123
											case '\n' :
2194
								if (this.scanner.getNextToken() == TerminalTokens.TokenNameCOMMENT_LINE) {
2195
									realTrailing = !hasLineComment;
2196
									switch (this.scanner.getNextToken()) {
2197
										case TerminalTokens.TokenNameCOMMENT_LINE:
2198
											// at least two contiguous line comments
2199
											// the formatter should not consider comments as trailing ones
2200
											realTrailing = false;
2201
											break;
2202
										case TerminalTokens.TokenNameWHITESPACE:
2203
											if (this.scanner.getNextToken() == TerminalTokens.TokenNameCOMMENT_LINE) {
2204
												// at least two contiguous line comments
2205
												// the formatter should not consider comments as trailing ones
2124
												realTrailing = false;
2206
												realTrailing = false;
2125
												break loop;
2207
											}
2126
										}
2208
											break;
2127
									}
2209
									}
2128
								}
2210
								}
2211
								this.scanner.resetTo(currentPosition, this.scanner.eofPosition - 1);
2129
							}
2212
							}
2130
							this.scanner.resetTo(currentPosition, this.scanner.eofPosition - 1);
2131
						}
2213
						}
2214
						// Look whether comments line may be contiguous or not
2215
						// Note that when preceding token is a comment line, then only one line
2216
						// is enough to have an empty line as the line end is included in the comment line...
2217
						// If comments are contiguous, store the white spaces to be able to compute the current comment indentation
2218
						if (lines > 1 || (lines == 1 && hasLineComment)) {
2219
							this.lastLineComment.contiguous = false;
2220
						}
2221
						this.lastLineComment.leadingSpaces = whiteSpaces;
2222
						this.lastLineComment.lines = lines;
2223
						// Strategy to consume spaces and eventually leave at this stage
2224
						// depends on the fact that a trailing comment is expected or not
2132
						if (realTrailing) {
2225
						if (realTrailing) {
2133
							// if a line comment is consumed, no other comment can be on the same line after
2226
							// if a line comment is consumed, no other comment can be on the same line after
2134
							if (hasLineComment) {
2227
							if (hasLineComment) {
Lines 2200-2205 Link Here
2200
							this.scanner.resetTo(this.scanner.getCurrentTokenStartPosition(), this.scannerEndPosition - 1);
2293
							this.scanner.resetTo(this.scanner.getCurrentTokenStartPosition(), this.scannerEndPosition - 1);
2201
							return;
2294
							return;
2202
						}
2295
						}
2296
						this.lastLineComment.contiguous = false;
2203
						if (rejectBlockComment) break;
2297
						if (rejectBlockComment) break;
2204
						if (lines >= 1) {
2298
						if (lines >= 1) {
2205
							if (lines > 1) {
2299
							if (lines > 1) {
Lines 2223-2228 Link Here
2223
							this.scanner.resetTo(this.scanner.getCurrentTokenStartPosition(), this.scannerEndPosition - 1);
2317
							this.scanner.resetTo(this.scanner.getCurrentTokenStartPosition(), this.scannerEndPosition - 1);
2224
							return;
2318
							return;
2225
						}
2319
						}
2320
						this.lastLineComment.contiguous = false;
2226
						if (rejectJavadocComment) break;
2321
						if (rejectJavadocComment) break;
2227
						if (lines >= 1) {
2322
						if (lines >= 1) {
2228
							if (lines > 1) {
2323
							if (lines > 1) {
Lines 2246-2251 Link Here
2246
						lines = 0;
2341
						lines = 0;
2247
						break;
2342
						break;
2248
					default :
2343
					default :
2344
						this.lastLineComment.contiguous = false;
2249
						// step back one token
2345
						// step back one token
2250
						this.scanner.resetTo(currentTokenStartPosition, this.scannerEndPosition - 1);
2346
						this.scanner.resetTo(currentTokenStartPosition, this.scannerEndPosition - 1);
2251
						return;
2347
						return;
Lines 2300-2311 Link Here
2300
    	int start = currentTokenStartPosition;
2396
    	int start = currentTokenStartPosition;
2301
    	int nextCharacterStart = currentTokenStartPosition;
2397
    	int nextCharacterStart = currentTokenStartPosition;
2302
2398
2303
    	if (this.indentationLevel != 0) {
2399
    	// Print comment line indentation
2304
    		if (!this.formatter.preferences.never_indent_line_comments_on_first_column
2400
    	int commentIndentationLevel;
2305
    				|| !isOnFirstColumn(start)) {
2401
    	if (this.indentationLevel == 0) {
2306
    			printIndentationIfNecessary();
2402
    		commentIndentationLevel = this.column - 1;
2403
    	} else {
2404
    		if (this.formatter.preferences.never_indent_line_comments_on_first_column &&
2405
    			isOnFirstColumn(start)) {
2406
	   			commentIndentationLevel = this.column - 1;
2407
    		} else {
2408
    			// Indentation may be specific for contiguous comment
2409
    			// see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=293300
2410
				if (this.lastLineComment.contiguous) {
2411
					// The leading spaces have been set while looping in the printComment(int) method
2412
					int currentCommentIndentation = getCurrentColumn(this.lastLineComment.leadingSpaces);
2413
					// Keep the current comment indentation when over the previous contiguous line comment
2414
					// and the previous comment has not been reindented
2415
					int lastCommentColumn = this.lastLineComment.currentColumn;
2416
					if (this.tabLength > 0) {
2417
						if ((currentCommentIndentation % this.tabLength) == 0) {
2418
							lastCommentColumn = (lastCommentColumn / this.tabLength) * this.tabLength;
2419
						} else {
2420
							currentCommentIndentation = ((currentCommentIndentation / this.tabLength) + 1) * this.tabLength;
2421
						}
2422
					}
2423
					if (currentCommentIndentation >= lastCommentColumn && this.lastLineComment.indentation != this.indentationLevel) {
2424
						int currentIndentationLevel = this.indentationLevel;
2425
						this.indentationLevel = this.lastLineComment.indentation ;
2426
						printIndentationIfNecessary();
2427
						this.indentationLevel = currentIndentationLevel;
2428
			   			commentIndentationLevel = this.lastLineComment.indentation ;
2429
					} else {
2430
						printIndentationIfNecessary();
2431
			   			commentIndentationLevel = this.column - 1;
2432
					}
2433
				} else {
2434
					if (this.currentAlignment != null && this.currentAlignment.name.equals("array_initializer") && //$NON-NLS-1$
2435
						this.indentationLevel < this.currentAlignment.breakIndentationLevel &&
2436
						this.lastLineComment.lines > 0)
2437
					{
2438
						int currentIndentationLevel = this.indentationLevel;
2439
						this.indentationLevel = this.currentAlignment.breakIndentationLevel;
2440
		    			printIndentationIfNecessary();
2441
						this.indentationLevel = currentIndentationLevel;
2442
			   			commentIndentationLevel = this.currentAlignment.breakIndentationLevel;
2443
					} else {
2444
		    			printIndentationIfNecessary();
2445
			   			commentIndentationLevel = this.column - 1;
2446
					}
2447
				}
2307
    		}
2448
    		}
2308
    	}
2449
    	}
2450
    	
2451
    	// Store line comment information
2452
   		this.lastLineComment.contiguous = true;
2453
		this.lastLineComment.currentColumn = getCurrentCommentColumn(currentTokenStartPosition);
2454
		this.lastLineComment.indentation = commentIndentationLevel;
2455
		
2456
		// Add pending space if necessary
2309
    	if (this.pendingSpace) {
2457
    	if (this.pendingSpace) {
2310
    		addInsertEdit(currentTokenStartPosition, " "); //$NON-NLS-1$
2458
    		addInsertEdit(currentTokenStartPosition, " "); //$NON-NLS-1$
2311
    	}
2459
    	}
Lines 3983-3988 Link Here
3983
		this.needSpace = false;
4131
		this.needSpace = false;
3984
		this.pendingSpace = false;
4132
		this.pendingSpace = false;
3985
		this.preserveLineBreakIndentation = false;
4133
		this.preserveLineBreakIndentation = false;
4134
		this.lastLineComment.contiguous = false;
3986
	}
4135
	}
3987
4136
3988
	public void printNextToken(int expectedTokenType){
4137
	public void printNextToken(int expectedTokenType){
(-)src/org/eclipse/jdt/core/tests/formatter/FormatterBugsTests.java (-5 / +1361 lines)
Lines 334-340 Link Here
334
		"\n" + 
334
		"\n" + 
335
		"public class X02 {\n" + 
335
		"public class X02 {\n" + 
336
		"}\n";
336
		"}\n";
337
	formatSource(source);
337
	formatSource(source,
338
		"import java.util.List;\n" + 
339
		"import java.util.Set;\n" + 
340
		"\n" + 
341
		"//import java.util.HashMap;\n" + 
342
		"\n" + 
343
		"public class X02 {\n" + 
344
		"}\n"
345
	);
338
}
346
}
339
public void testBug199265c1() throws JavaModelException {
347
public void testBug199265c1() throws JavaModelException {
340
	String source =
348
	String source =
Lines 379-384 Link Here
379
		"}\n";
387
		"}\n";
380
	formatSource(source);
388
	formatSource(source);
381
}
389
}
390
public void testBug199265d1() throws JavaModelException {
391
	String source =
392
		"import java.util.Set; // trailing comment\n" + 
393
		"// line comment\n" + 
394
		"import java.util.Map; // trailing comment\n" + 
395
		"// line comment\n" + 
396
		"public class X04 {\n" + 
397
		"\n" + 
398
		"}\n";
399
	formatSource(source,
400
		"import java.util.Set; // trailing comment\n" + 
401
		"// line comment\n" + 
402
		"import java.util.Map; // trailing comment\n" + 
403
		"// line comment\n" + 
404
		"\n" + 
405
		"public class X04 {\n" + 
406
		"\n" + 
407
		"}\n"
408
	);
409
}
410
public void testBug199265d2() throws JavaModelException {
411
	String source =
412
		"import java.util.Set; // trailing comment\n" + 
413
		"// line comment\n" + 
414
		"import java.util.Map; // trailing comment\n" + 
415
		"// line comment\n" + 
416
		"\n" + 
417
		"public class X04 {\n" + 
418
		"\n" + 
419
		"}\n";
420
	formatSource(source);
421
}
422
public void testBug199265d3() throws JavaModelException {
423
	String source =
424
		"import java.util.Set; // trailing comment\n" + 
425
		"	// line comment\n" + 
426
		"import java.util.Map; // trailing comment\n" + 
427
		"	// line comment\n" + 
428
		"public class X04 {\n" + 
429
		"\n" + 
430
		"}\n";
431
	formatSource(source,
432
		"import java.util.Set; // trailing comment\n" + 
433
		"// line comment\n" + 
434
		"import java.util.Map; // trailing comment\n" + 
435
		"// line comment\n" + 
436
		"\n" + 
437
		"public class X04 {\n" + 
438
		"\n" + 
439
		"}\n"
440
	);
441
}
382
public void testBug199265_wksp1a() throws JavaModelException {
442
public void testBug199265_wksp1a() throws JavaModelException {
383
	String source =
443
	String source =
384
		"package wksp1;\n" + 
444
		"package wksp1;\n" + 
Lines 837-843 Link Here
837
	String source =
897
	String source =
838
		"package massive;\n" +
898
		"package massive;\n" +
839
		"\n" +
899
		"\n" +
840
		"public class X05b\n" +
900
		"public class X05\n" +
841
		"{\n" +
901
		"{\n" +
842
		"\n" +
902
		"\n" +
843
		"    public void foo() throws NullPointerException {\n" +
903
		"    public void foo() throws NullPointerException {\n" +
Lines 859-865 Link Here
859
	formatSource(source,
919
	formatSource(source,
860
		"package massive;\n" +
920
		"package massive;\n" +
861
		"\n" +
921
		"\n" +
862
		"public class X05b {\n" +
922
		"public class X05 {\n" +
863
		"\n" +
923
		"\n" +
864
		"	public void foo() throws NullPointerException {\n" +
924
		"	public void foo() throws NullPointerException {\n" +
865
		"\n" +
925
		"\n" +
Lines 888-894 Link Here
888
	String source =
948
	String source =
889
		"package massive;\n" +
949
		"package massive;\n" +
890
		"\n" +
950
		"\n" +
891
		"public class X05b\n" +
951
		"public class X05\n" +
892
		"{\n" +
952
		"{\n" +
893
		"\n" +
953
		"\n" +
894
		"    public void foo() throws NullPointerException {\n" +
954
		"    public void foo() throws NullPointerException {\n" +
Lines 910-916 Link Here
910
	formatSource(source,
970
	formatSource(source,
911
		"package massive;\n" +
971
		"package massive;\n" +
912
		"\n" +
972
		"\n" +
913
		"public class X05b\n" +
973
		"public class X05\n" +
914
		"{\n" +
974
		"{\n" +
915
		"\n" +
975
		"\n" +
916
		"	public void foo() throws NullPointerException\n" +
976
		"	public void foo() throws NullPointerException\n" +
Lines 1555-1560 Link Here
1555
}
1615
}
1556
1616
1557
/**
1617
/**
1618
 * @bug 293300: [formatter] The formatter is still unstable in certain circumstances
1619
 * @test Verify that formatting twice a compilation unit does not produce different output
1620
 * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=293300"
1621
 */
1622
public void testBug293300_wksp1_01() {
1623
	String source = 
1624
		"package wksp1;\n" + 
1625
		"\n" + 
1626
		"public class X01 {\n" + 
1627
		"\n" + 
1628
		"	boolean foo(int test, int value) {\n" + 
1629
		"		// This comment may also be impacted after having been split in several lines. Furthermore, it\'s also important to verify that the algorithm works when the comment is split into several lines. It\'s a common use case that it may works for 1, 2 but not for 3 iterations...\n" + 
1630
		"		if (test == 0) {\n" + 
1631
		"			// skip\n" + 
1632
		"		} else if (Math.sqrt(Math.pow(test, 2)) > 10) // This is the offending comment after having been split into several lines\n" + 
1633
		"			return false;\n" + 
1634
		"		return true;\n" + 
1635
		"	}\n" + 
1636
		"}\n";
1637
	formatSource(source,
1638
		"package wksp1;\n" + 
1639
		"\n" + 
1640
		"public class X01 {\n" + 
1641
		"\n" + 
1642
		"	boolean foo(int test, int value) {\n" + 
1643
		"		// This comment may also be impacted after having been split in several\n" + 
1644
		"		// lines. Furthermore, it\'s also important to verify that the algorithm\n" + 
1645
		"		// works when the comment is split into several lines. It\'s a common use\n" + 
1646
		"		// case that it may works for 1, 2 but not for 3 iterations...\n" + 
1647
		"		if (test == 0) {\n" + 
1648
		"			// skip\n" + 
1649
		"		} else if (Math.sqrt(Math.pow(test, 2)) > 10) // This is the offending\n" + 
1650
		"														// comment after having\n" + 
1651
		"														// been split into\n" + 
1652
		"														// several lines\n" + 
1653
		"			return false;\n" + 
1654
		"		return true;\n" + 
1655
		"	}\n" + 
1656
		"}\n"
1657
	);
1658
}
1659
public void testBug293300_wkps1_02() {
1660
	String source = 
1661
		"package wksp1;\n" + 
1662
		"\n" + 
1663
		"public class X02 {\n" + 
1664
		"	String field;\n" + 
1665
		"	 public X02(String test) {\n" + 
1666
		"		field= test.toLowerCase();\n" + 
1667
		"		try {\n" + 
1668
		"			testWhetherItWorksOrNot(test); // This comment will be split and should not involve instability\n" + 
1669
		"		} catch (Exception e) {\n" + 
1670
		"			return;\n" + 
1671
		"		}\n" + 
1672
		"	 }\n" + 
1673
		"	private void testWhetherItWorksOrNot(String test) {\n" + 
1674
		"	}\n" + 
1675
		"}\n";
1676
	formatSource(source,
1677
		"package wksp1;\n" + 
1678
		"\n" + 
1679
		"public class X02 {\n" + 
1680
		"	String field;\n" + 
1681
		"\n" + 
1682
		"	public X02(String test) {\n" + 
1683
		"		field = test.toLowerCase();\n" + 
1684
		"		try {\n" + 
1685
		"			testWhetherItWorksOrNot(test); // This comment will be split and\n" + 
1686
		"											// should not involve instability\n" + 
1687
		"		} catch (Exception e) {\n" + 
1688
		"			return;\n" + 
1689
		"		}\n" + 
1690
		"	}\n" + 
1691
		"\n" + 
1692
		"	private void testWhetherItWorksOrNot(String test) {\n" + 
1693
		"	}\n" + 
1694
		"}\n"
1695
	);
1696
}
1697
public void testBug293300_wkps1_03() {
1698
	String source = 
1699
		"package wksp1;\n" + 
1700
		"\n" + 
1701
		"public class X03 {\n" + 
1702
		"public static final native int foo(\n" + 
1703
		"	int firstParameter,\n" + 
1704
		"	int secondParameter,\n" + 
1705
		"	int[] param3);        //When a long comment is placed here with at least one line to follow,\n" + 
1706
		"						  //    the second line may be difficult to be formatted correctly\n" + 
1707
		"public static final native int bar();\n" + 
1708
		"\n" + 
1709
		"}\n";
1710
	formatSource(source,
1711
		"package wksp1;\n" + 
1712
		"\n" + 
1713
		"public class X03 {\n" + 
1714
		"	public static final native int foo(int firstParameter, int secondParameter,\n" + 
1715
		"			int[] param3); // When a long comment is placed here with at least\n" + 
1716
		"							// one line to follow,\n" + 
1717
		"							// the second line may be difficult to be formatted\n" + 
1718
		"							// correctly\n" + 
1719
		"\n" + 
1720
		"	public static final native int bar();\n" + 
1721
		"\n" + 
1722
		"}\n"
1723
	);
1724
}
1725
public void testBug293300_wkps1_04() {
1726
	String source = 
1727
		"package wksp1;\n" + 
1728
		"\n" + 
1729
		"interface Y04_____________________________ {\n" + 
1730
		"}\n" + 
1731
		"\n" + 
1732
		"public interface X04 extends Y04_____________________________ { // modifier constant\n" + 
1733
		"	// those constants are depending upon ClassFileConstants (relying that classfiles only use the 16 lower bits)\n" + 
1734
		"	final int AccDefault = 0;\n" + 
1735
		"}\n";
1736
	formatSource(source,
1737
		"package wksp1;\n" + 
1738
		"\n" + 
1739
		"interface Y04_____________________________ {\n" + 
1740
		"}\n" + 
1741
		"\n" + 
1742
		"public interface X04 extends Y04_____________________________ { // modifier\n" + 
1743
		"																// constant\n" + 
1744
		"	// those constants are depending upon ClassFileConstants (relying that\n" + 
1745
		"	// classfiles only use the 16 lower bits)\n" + 
1746
		"	final int AccDefault = 0;\n" + 
1747
		"}\n"
1748
	);
1749
}
1750
public void testBug293300_wkps1_05() {
1751
	String source = 
1752
		"package wksp1;\n" + 
1753
		"\n" + 
1754
		"public class X05 {\n" + 
1755
		"	private final static String[] TEST_BUG = {\"a\", //$NON-NLS-1$\n" + 
1756
		"			\"b\", //$NON-NLS-1$\n" + 
1757
		"			\"c\", //$NON-NLS-1$\n" + 
1758
		"	};\n" + 
1759
		"}\n";
1760
	formatSource(source,
1761
		"package wksp1;\n" + 
1762
		"\n" + 
1763
		"public class X05 {\n" + 
1764
		"	private final static String[] TEST_BUG = { \"a\", //$NON-NLS-1$\n" + 
1765
		"			\"b\", //$NON-NLS-1$\n" + 
1766
		"			\"c\", //$NON-NLS-1$\n" + 
1767
		"	};\n" + 
1768
		"}\n"
1769
	);
1770
}
1771
public void testBug293300_wkps1_05_JoinLinesComments_BracesNextLine() {
1772
	this.formatterPrefs.join_wrapped_lines = false;
1773
	setUpBracesPreferences(DefaultCodeFormatterConstants.NEXT_LINE);
1774
	String source = 
1775
		"package wksp1;\n" + 
1776
		"\n" + 
1777
		"public class X05 {\n" + 
1778
		"	private final static String[] TEST_BUG = {\"a\", //$NON-NLS-1$\n" + 
1779
		"			\"b\", //$NON-NLS-1$\n" + 
1780
		"			\"c\", //$NON-NLS-1$\n" + 
1781
		"	};\n" + 
1782
		"}\n";
1783
	formatSource(source,
1784
		"package wksp1;\n" + 
1785
		"\n" + 
1786
		"public class X05\n" + 
1787
		"{\n" + 
1788
		"	private final static String[] TEST_BUG =\n" + 
1789
		"	{ \"a\", //$NON-NLS-1$\n" + 
1790
		"			\"b\", //$NON-NLS-1$\n" + 
1791
		"			\"c\", //$NON-NLS-1$\n" + 
1792
		"	};\n" + 
1793
		"}\n"
1794
	);
1795
}
1796
public void testBug293300_wksp2_01() {
1797
	String source = 
1798
		"package wksp2;\n" + 
1799
		"\n" + 
1800
		"public class X01 {\n" + 
1801
		"\n" + 
1802
		"	protected String foo(String[] tests) {\n" + 
1803
		"		String result = null;\n" + 
1804
		"		for (int i = 0; i < tests.length; i++) {\n" + 
1805
		"			String test = tests[i];\n" + 
1806
		"			if (test.startsWith(\"test\")) { //$NON-NLS-1$\n" + 
1807
		"				//we got the malformed tree exception here\n" + 
1808
		"				result = test;\n" + 
1809
		"			}\n" + 
1810
		"		}\n" + 
1811
		"		return result;\n" + 
1812
		"	}\n" + 
1813
		"\n" + 
1814
		"}\n";
1815
	formatSource(source,
1816
		"package wksp2;\n" + 
1817
		"\n" + 
1818
		"public class X01 {\n" + 
1819
		"\n" + 
1820
		"	protected String foo(String[] tests) {\n" + 
1821
		"		String result = null;\n" + 
1822
		"		for (int i = 0; i < tests.length; i++) {\n" + 
1823
		"			String test = tests[i];\n" + 
1824
		"			if (test.startsWith(\"test\")) { //$NON-NLS-1$\n" + 
1825
		"				// we got the malformed tree exception here\n" + 
1826
		"				result = test;\n" + 
1827
		"			}\n" + 
1828
		"		}\n" + 
1829
		"		return result;\n" + 
1830
		"	}\n" + 
1831
		"\n" + 
1832
		"}\n"
1833
	);
1834
}
1835
public void testBug293300_wksp2_02() {
1836
	String source = 
1837
		"package wksp2;\n" + 
1838
		"\n" + 
1839
		"public class X02 {\n" + 
1840
		"\n" + 
1841
		"\n" + 
1842
		"	public void foo(int kind) {\n" + 
1843
		"		switch (kind) {\n" + 
1844
		"			case 0 :\n" + 
1845
		"				break;\n" + 
1846
		"			case 1 :\n" + 
1847
		"				//the first formatting looks strange on this already splitted\n" + 
1848
		"				// comment\n" + 
1849
		"				if (true)\n" + 
1850
		"					return;\n" + 
1851
		"			//fall through\n" + 
1852
		"			default:\n" + 
1853
		"				if (kind < 0)\n" + 
1854
		"					return;\n" + 
1855
		"				break;\n" + 
1856
		"		}\n" + 
1857
		"	}\n" + 
1858
		"\n" + 
1859
		"}\n";
1860
	formatSource(source,
1861
		"package wksp2;\n" + 
1862
		"\n" + 
1863
		"public class X02 {\n" + 
1864
		"\n" + 
1865
		"	public void foo(int kind) {\n" + 
1866
		"		switch (kind) {\n" + 
1867
		"		case 0:\n" + 
1868
		"			break;\n" + 
1869
		"		case 1:\n" + 
1870
		"			// the first formatting looks strange on this already splitted\n" + 
1871
		"			// comment\n" + 
1872
		"			if (true)\n" + 
1873
		"				return;\n" + 
1874
		"			// fall through\n" + 
1875
		"		default:\n" + 
1876
		"			if (kind < 0)\n" + 
1877
		"				return;\n" + 
1878
		"			break;\n" + 
1879
		"		}\n" + 
1880
		"	}\n" + 
1881
		"\n" + 
1882
		"}\n"
1883
	);
1884
}
1885
public void testBug293300_wksp2_03() {
1886
	String source = 
1887
		"package wksp2;\n" + 
1888
		"\n" + 
1889
		"public class X03 {\n" + 
1890
		"	public byte[] foo(byte value) {\n" + 
1891
		"		byte[] result = new byte[10];\n" + 
1892
		"		int valTest = 0;\n" + 
1893
		"		switch (value) {\n" + 
1894
		"			case 1 :\n" + 
1895
		"				for (int j = 10; j >= 0; j--) {\n" + 
1896
		"					result[j] = (byte) (valTest & 0xff); // Bottom 8\n" + 
1897
		"					// bits\n" + 
1898
		"					valTest = valTest >>> 2;\n" + 
1899
		"				}\n" + 
1900
		"				break;\n" + 
1901
		"		}\n" + 
1902
		"		return result;\n" + 
1903
		"	}\n" + 
1904
		"}\n";
1905
	formatSource(source,
1906
		"package wksp2;\n" + 
1907
		"\n" + 
1908
		"public class X03 {\n" + 
1909
		"	public byte[] foo(byte value) {\n" + 
1910
		"		byte[] result = new byte[10];\n" + 
1911
		"		int valTest = 0;\n" + 
1912
		"		switch (value) {\n" + 
1913
		"		case 1:\n" + 
1914
		"			for (int j = 10; j >= 0; j--) {\n" + 
1915
		"				result[j] = (byte) (valTest & 0xff); // Bottom 8\n" + 
1916
		"				// bits\n" + 
1917
		"				valTest = valTest >>> 2;\n" + 
1918
		"			}\n" + 
1919
		"			break;\n" + 
1920
		"		}\n" + 
1921
		"		return result;\n" + 
1922
		"	}\n" + 
1923
		"}\n"
1924
	);
1925
}
1926
public void testBug293300_wksp2_04() {
1927
	String source = 
1928
		"package wksp2;\n" + 
1929
		"\n" + 
1930
		"public class X04 {\n" + 
1931
		"\n" + 
1932
		"	void foo() {\n" + 
1933
		"		int lastDiagonal[]= new int[1000000 + 1]; // this line comments configuration\n" + 
1934
		"		// may screw up the formatter to know which one\n" + 
1935
		"		int origin= 1000000 / 2; // needs to stay at its current indentation or not\n" + 
1936
		"	}\n" + 
1937
		"}\n";
1938
	formatSource(source,
1939
		"package wksp2;\n" + 
1940
		"\n" + 
1941
		"public class X04 {\n" + 
1942
		"\n" + 
1943
		"	void foo() {\n" + 
1944
		"		int lastDiagonal[] = new int[1000000 + 1]; // this line comments\n" + 
1945
		"													// configuration\n" + 
1946
		"		// may screw up the formatter to know which one\n" + 
1947
		"		int origin = 1000000 / 2; // needs to stay at its current indentation or\n" + 
1948
		"									// not\n" + 
1949
		"	}\n" + 
1950
		"}\n"
1951
	);
1952
}
1953
private static final String EXPECTED_OUTPUT_WKSP2E1 =
1954
	"package wksp2;\n" + 
1955
	"\n" + 
1956
	"public class X05 {\n" + 
1957
	"	void foo(int val) {\n" + 
1958
	"		try {\n" + 
1959
	"			loop: for (int i = 0; i < 10; i++) {\n" + 
1960
	"				switch (val) {\n" + 
1961
	"				case 1:\n" + 
1962
	"					if (i == 0) {\n" + 
1963
	"						if (true) {\n" + 
1964
	"							val++;\n" + 
1965
	"						} // these comments\n" + 
1966
	"							// may be wrongly\n" + 
1967
	"							// realigned\n" + 
1968
	"							// by the formatter\n" + 
1969
	"\n" + 
1970
	"						// other comment\n" + 
1971
	"						val--;\n" + 
1972
	"						continue loop;\n" + 
1973
	"					}\n" + 
1974
	"				default:\n" + 
1975
	"					throw new IllegalArgumentException();\n" + 
1976
	"				}\n" + 
1977
	"			}\n" + 
1978
	"		} finally {\n" + 
1979
	"		}\n" + 
1980
	"	}\n" + 
1981
	"}\n";
1982
public void testBug293300_wksp2_05() {
1983
	String source = 
1984
		"package wksp2;\n" + 
1985
		"\n" + 
1986
		"public class X05 {\n" + 
1987
		"	void foo(int val) {\n" + 
1988
		"		try {\n" + 
1989
		"			loop: for (int i=0; i<10; i++) {\n" + 
1990
		"				switch (val) {\n" + 
1991
		"					case 1 :\n" + 
1992
		"						if (i==0) {\n" + 
1993
		"							if (true) {\n" + 
1994
		"								val++;\n" + 
1995
		"							} //these comments\n" + 
1996
		"							// may be wrongly\n" + 
1997
		"							// realigned\n" + 
1998
		"							// by the formatter\n" + 
1999
		"\n" + 
2000
		"							// other comment\n" + 
2001
		"							val--;\n" + 
2002
		"							continue loop;\n" + 
2003
		"						}\n" + 
2004
		"					default :\n" + 
2005
		"						throw new IllegalArgumentException();\n" + 
2006
		"				}\n" + 
2007
		"			}\n" + 
2008
		"		}\n" + 
2009
		"		finally {\n" + 
2010
		"		}\n" + 
2011
		"	}\n" + 
2012
		"}\n";
2013
	formatSource(source, EXPECTED_OUTPUT_WKSP2E1);
2014
}
2015
public void testBug293300_wksp2_05b() {
2016
	String source = 
2017
		"package wksp2;\n" + 
2018
		"\n" + 
2019
		"public class X05 {\n" + 
2020
		"	void foo(int val) {\n" + 
2021
		"		try {\n" + 
2022
		"			loop: for (int i=0; i<10; i++) {\n" + 
2023
		"				switch (val) {\n" + 
2024
		"					case 1 :\n" + 
2025
		"						if (i==0) {\n" + 
2026
		"							if (true) {\n" + 
2027
		"								val++;\n" + 
2028
		"							} //these comments\n" + 
2029
		"							 // may be wrongly\n" + 
2030
		"							 // realigned\n" + 
2031
		"							 // by the formatter\n" + 
2032
		"\n" + 
2033
		"							// other comment\n" + 
2034
		"							val--;\n" + 
2035
		"							continue loop;\n" + 
2036
		"						}\n" + 
2037
		"					default :\n" + 
2038
		"						throw new IllegalArgumentException();\n" + 
2039
		"				}\n" + 
2040
		"			}\n" + 
2041
		"		}\n" + 
2042
		"		finally {\n" + 
2043
		"		}\n" + 
2044
		"	}\n" + 
2045
		"}\n";
2046
	formatSource(source, EXPECTED_OUTPUT_WKSP2E1);
2047
}
2048
private static final String EXPECTED_OUTPUT_WKSP2E3 =
2049
	"package wksp2;\n" + 
2050
	"\n" + 
2051
	"public class X05 {\n" + 
2052
	"	void foo(int val) {\n" + 
2053
	"		try {\n" + 
2054
	"			loop: for (int i = 0; i < 10; i++) {\n" + 
2055
	"				switch (val) {\n" + 
2056
	"				case 1:\n" + 
2057
	"					if (i == 0) {\n" + 
2058
	"						if (true) {\n" + 
2059
	"							val++;\n" + 
2060
	"						} // these comments\n" + 
2061
	"							// may be wrongly\n" + 
2062
	"							// realigned\n" + 
2063
	"							// by the formatter\n" + 
2064
	"\n" + 
2065
	"						// other comment\n" + 
2066
	"						val--;\n" + 
2067
	"						continue loop;\n" + 
2068
	"					}\n" + 
2069
	"				default:\n" + 
2070
	"					throw new IllegalArgumentException();\n" + 
2071
	"				}\n" + 
2072
	"			}\n" + 
2073
	"		} finally {\n" + 
2074
	"		}\n" + 
2075
	"	}\n" + 
2076
	"}\n";
2077
public void testBug293300_wksp2_05c() {
2078
	String source = 
2079
		"package wksp2;\n" + 
2080
		"\n" + 
2081
		"public class X05 {\n" + 
2082
		"	void foo(int val) {\n" + 
2083
		"		try {\n" + 
2084
		"			loop: for (int i=0; i<10; i++) {\n" + 
2085
		"				switch (val) {\n" + 
2086
		"					case 1 :\n" + 
2087
		"						if (i==0) {\n" + 
2088
		"							if (true) {\n" + 
2089
		"								val++;\n" + 
2090
		"							} //these comments\n" + 
2091
		"							  // may be wrongly\n" + 
2092
		"							  // realigned\n" + 
2093
		"							  // by the formatter\n" + 
2094
		"\n" + 
2095
		"							// other comment\n" + 
2096
		"							val--;\n" + 
2097
		"							continue loop;\n" + 
2098
		"						}\n" + 
2099
		"					default :\n" + 
2100
		"						throw new IllegalArgumentException();\n" + 
2101
		"				}\n" + 
2102
		"			}\n" + 
2103
		"		}\n" + 
2104
		"		finally {\n" + 
2105
		"		}\n" + 
2106
		"	}\n" + 
2107
		"}\n";
2108
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3);
2109
}
2110
public void testBug293300_wksp2_05d() {
2111
	String source = 
2112
		"package wksp2;\n" + 
2113
		"\n" + 
2114
		"public class X05 {\n" + 
2115
		"	void foo(int val) {\n" + 
2116
		"		try {\n" + 
2117
		"			loop: for (int i=0; i<10; i++) {\n" + 
2118
		"				switch (val) {\n" + 
2119
		"					case 1 :\n" + 
2120
		"						if (i==0) {\n" + 
2121
		"							if (true) {\n" + 
2122
		"								val++;\n" + 
2123
		"							} //these comments\n" + 
2124
		"							   // may be wrongly\n" + 
2125
		"							   // realigned\n" + 
2126
		"							   // by the formatter\n" + 
2127
		"\n" + 
2128
		"							// other comment\n" + 
2129
		"							val--;\n" + 
2130
		"							continue loop;\n" + 
2131
		"						}\n" + 
2132
		"					default :\n" + 
2133
		"						throw new IllegalArgumentException();\n" + 
2134
		"				}\n" + 
2135
		"			}\n" + 
2136
		"		}\n" + 
2137
		"		finally {\n" + 
2138
		"		}\n" + 
2139
		"	}\n" + 
2140
		"}\n";
2141
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3);
2142
}
2143
public void testBug293300_wksp2_05e() {
2144
	String source = 
2145
		"package wksp2;\n" + 
2146
		"\n" + 
2147
		"public class X05 {\n" + 
2148
		"	void foo(int val) {\n" + 
2149
		"		try {\n" + 
2150
		"			loop: for (int i=0; i<10; i++) {\n" + 
2151
		"				switch (val) {\n" + 
2152
		"					case 1 :\n" + 
2153
		"						if (i==0) {\n" + 
2154
		"							if (true) {\n" + 
2155
		"								val++;\n" + 
2156
		"							} //these comments\n" + 
2157
		"								// may be wrongly\n" + 
2158
		"								// realigned\n" + 
2159
		"								// by the formatter\n" + 
2160
		"\n" + 
2161
		"							// other comment\n" + 
2162
		"							val--;\n" + 
2163
		"							continue loop;\n" + 
2164
		"						}\n" + 
2165
		"					default :\n" + 
2166
		"						throw new IllegalArgumentException();\n" + 
2167
		"				}\n" + 
2168
		"			}\n" + 
2169
		"		}\n" + 
2170
		"		finally {\n" + 
2171
		"		}\n" + 
2172
		"	}\n" + 
2173
		"}\n";
2174
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3);
2175
}
2176
private static final String EXPECTED_OUTPUT_WKSP2E1_SPACES =
2177
	"package wksp2;\n" + 
2178
	"\n" + 
2179
	"public class X05 {\n" + 
2180
	"    void foo(int val) {\n" + 
2181
	"        try {\n" + 
2182
	"            loop: for (int i = 0; i < 10; i++) {\n" + 
2183
	"                switch (val) {\n" + 
2184
	"                case 1:\n" + 
2185
	"                    if (i == 0) {\n" + 
2186
	"                        if (true) {\n" + 
2187
	"                            val++;\n" + 
2188
	"                        } // these comments\n" + 
2189
	"                          // may be wrongly\n" + 
2190
	"                          // realigned\n" + 
2191
	"                          // by the formatter\n" + 
2192
	"\n" + 
2193
	"                        // other comment\n" + 
2194
	"                        val--;\n" + 
2195
	"                        continue loop;\n" + 
2196
	"                    }\n" + 
2197
	"                default:\n" + 
2198
	"                    throw new IllegalArgumentException();\n" + 
2199
	"                }\n" + 
2200
	"            }\n" + 
2201
	"        } finally {\n" + 
2202
	"        }\n" + 
2203
	"    }\n" + 
2204
	"}\n";
2205
public void testBug293300_wksp2_05_spaces() {
2206
	this.formatterPrefs.tab_char = DefaultCodeFormatterOptions.SPACE;
2207
	String source = 
2208
		"package wksp2;\n" + 
2209
		"\n" + 
2210
		"public class X05 {\n" + 
2211
		"	void foo(int val) {\n" + 
2212
		"		try {\n" + 
2213
		"			loop: for (int i=0; i<10; i++) {\n" + 
2214
		"				switch (val) {\n" + 
2215
		"					case 1 :\n" + 
2216
		"						if (i==0) {\n" + 
2217
		"							if (true) {\n" + 
2218
		"								val++;\n" + 
2219
		"							} //these comments\n" + 
2220
		"							// may be wrongly\n" + 
2221
		"							// realigned\n" + 
2222
		"							// by the formatter\n" + 
2223
		"\n" + 
2224
		"							// other comment\n" + 
2225
		"							val--;\n" + 
2226
		"							continue loop;\n" + 
2227
		"						}\n" + 
2228
		"					default :\n" + 
2229
		"						throw new IllegalArgumentException();\n" + 
2230
		"				}\n" + 
2231
		"			}\n" + 
2232
		"		}\n" + 
2233
		"		finally {\n" + 
2234
		"		}\n" + 
2235
		"	}\n" + 
2236
		"}\n";
2237
	formatSource(source, EXPECTED_OUTPUT_WKSP2E1_SPACES);
2238
}
2239
public void testBug293300_wksp2_05b_spaces() {
2240
	this.formatterPrefs.tab_char = DefaultCodeFormatterOptions.SPACE;
2241
	String source = 
2242
		"package wksp2;\n" + 
2243
		"\n" + 
2244
		"public class X05 {\n" + 
2245
		"	void foo(int val) {\n" + 
2246
		"		try {\n" + 
2247
		"			loop: for (int i=0; i<10; i++) {\n" + 
2248
		"				switch (val) {\n" + 
2249
		"					case 1 :\n" + 
2250
		"						if (i==0) {\n" + 
2251
		"							if (true) {\n" + 
2252
		"								val++;\n" + 
2253
		"							} //these comments\n" + 
2254
		"							 // may be wrongly\n" + 
2255
		"							 // realigned\n" + 
2256
		"							 // by the formatter\n" + 
2257
		"\n" + 
2258
		"							// other comment\n" + 
2259
		"							val--;\n" + 
2260
		"							continue loop;\n" + 
2261
		"						}\n" + 
2262
		"					default :\n" + 
2263
		"						throw new IllegalArgumentException();\n" + 
2264
		"				}\n" + 
2265
		"			}\n" + 
2266
		"		}\n" + 
2267
		"		finally {\n" + 
2268
		"		}\n" + 
2269
		"	}\n" + 
2270
		"}\n";
2271
	formatSource(source, EXPECTED_OUTPUT_WKSP2E1_SPACES);
2272
}
2273
private static final String EXPECTED_OUTPUT_WKSP2E3_SPACES =
2274
	"package wksp2;\n" + 
2275
	"\n" + 
2276
	"public class X05 {\n" + 
2277
	"    void foo(int val) {\n" + 
2278
	"        try {\n" + 
2279
	"            loop: for (int i = 0; i < 10; i++) {\n" + 
2280
	"                switch (val) {\n" + 
2281
	"                case 1:\n" + 
2282
	"                    if (i == 0) {\n" + 
2283
	"                        if (true) {\n" + 
2284
	"                            val++;\n" + 
2285
	"                        } // these comments\n" + 
2286
	"                          // may be wrongly\n" + 
2287
	"                          // realigned\n" + 
2288
	"                          // by the formatter\n" + 
2289
	"\n" + 
2290
	"                        // other comment\n" + 
2291
	"                        val--;\n" + 
2292
	"                        continue loop;\n" + 
2293
	"                    }\n" + 
2294
	"                default:\n" + 
2295
	"                    throw new IllegalArgumentException();\n" + 
2296
	"                }\n" + 
2297
	"            }\n" + 
2298
	"        } finally {\n" + 
2299
	"        }\n" + 
2300
	"    }\n" + 
2301
	"}\n";
2302
public void testBug293300_wksp2_05c_spaces() {
2303
	this.formatterPrefs.tab_char = DefaultCodeFormatterOptions.SPACE;
2304
	String source = 
2305
		"package wksp2;\n" + 
2306
		"\n" + 
2307
		"public class X05 {\n" + 
2308
		"	void foo(int val) {\n" + 
2309
		"		try {\n" + 
2310
		"			loop: for (int i=0; i<10; i++) {\n" + 
2311
		"				switch (val) {\n" + 
2312
		"					case 1 :\n" + 
2313
		"						if (i==0) {\n" + 
2314
		"							if (true) {\n" + 
2315
		"								val++;\n" + 
2316
		"							} //these comments\n" + 
2317
		"							  // may be wrongly\n" + 
2318
		"							  // realigned\n" + 
2319
		"							  // by the formatter\n" + 
2320
		"\n" + 
2321
		"							// other comment\n" + 
2322
		"							val--;\n" + 
2323
		"							continue loop;\n" + 
2324
		"						}\n" + 
2325
		"					default :\n" + 
2326
		"						throw new IllegalArgumentException();\n" + 
2327
		"				}\n" + 
2328
		"			}\n" + 
2329
		"		}\n" + 
2330
		"		finally {\n" + 
2331
		"		}\n" + 
2332
		"	}\n" + 
2333
		"}\n";
2334
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3_SPACES);
2335
}
2336
public void testBug293300_wksp2_05d_spaces() {
2337
	this.formatterPrefs.tab_char = DefaultCodeFormatterOptions.SPACE;
2338
	String source = 
2339
		"package wksp2;\n" + 
2340
		"\n" + 
2341
		"public class X05 {\n" + 
2342
		"	void foo(int val) {\n" + 
2343
		"		try {\n" + 
2344
		"			loop: for (int i=0; i<10; i++) {\n" + 
2345
		"				switch (val) {\n" + 
2346
		"					case 1 :\n" + 
2347
		"						if (i==0) {\n" + 
2348
		"							if (true) {\n" + 
2349
		"								val++;\n" + 
2350
		"							} //these comments\n" + 
2351
		"							   // may be wrongly\n" + 
2352
		"							   // realigned\n" + 
2353
		"							   // by the formatter\n" + 
2354
		"\n" + 
2355
		"							// other comment\n" + 
2356
		"							val--;\n" + 
2357
		"							continue loop;\n" + 
2358
		"						}\n" + 
2359
		"					default :\n" + 
2360
		"						throw new IllegalArgumentException();\n" + 
2361
		"				}\n" + 
2362
		"			}\n" + 
2363
		"		}\n" + 
2364
		"		finally {\n" + 
2365
		"		}\n" + 
2366
		"	}\n" + 
2367
		"}\n";
2368
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3_SPACES);
2369
}
2370
public void testBug293300_wksp2_05e_spaces() {
2371
	this.formatterPrefs.tab_char = DefaultCodeFormatterOptions.SPACE;
2372
	String source = 
2373
		"package wksp2;\n" + 
2374
		"\n" + 
2375
		"public class X05 {\n" + 
2376
		"	void foo(int val) {\n" + 
2377
		"		try {\n" + 
2378
		"			loop: for (int i=0; i<10; i++) {\n" + 
2379
		"				switch (val) {\n" + 
2380
		"					case 1 :\n" + 
2381
		"						if (i==0) {\n" + 
2382
		"							if (true) {\n" + 
2383
		"								val++;\n" + 
2384
		"							} //these comments\n" + 
2385
		"								// may be wrongly\n" + 
2386
		"								// realigned\n" + 
2387
		"								// by the formatter\n" + 
2388
		"\n" + 
2389
		"							// other comment\n" + 
2390
		"							val--;\n" + 
2391
		"							continue loop;\n" + 
2392
		"						}\n" + 
2393
		"					default :\n" + 
2394
		"						throw new IllegalArgumentException();\n" + 
2395
		"				}\n" + 
2396
		"			}\n" + 
2397
		"		}\n" + 
2398
		"		finally {\n" + 
2399
		"		}\n" + 
2400
		"	}\n" + 
2401
		"}\n";
2402
	formatSource(source, EXPECTED_OUTPUT_WKSP2E3_SPACES);
2403
}
2404
public void testBug293300_wksp_06() {
2405
	String source = 
2406
		"package wksp2;\n" + 
2407
		"\n" + 
2408
		"public class X06 {\n" + 
2409
		"public static final native int foo(\n" + 
2410
		"	String field,        //First field\n" + 
2411
		"	int[] array);        //This comment may cause trouble for the formatter, especially if there\'s another\n" + 
2412
		"						  //    line below  \n" + 
2413
		"public static final native int bar();\n" + 
2414
		"}\n";
2415
	formatSource(source,
2416
		"package wksp2;\n" + 
2417
		"\n" + 
2418
		"public class X06 {\n" + 
2419
		"	public static final native int foo(String field, // First field\n" + 
2420
		"			int[] array); // This comment may cause trouble for the formatter,\n" + 
2421
		"							// especially if there\'s another\n" + 
2422
		"							// line below\n" + 
2423
		"\n" + 
2424
		"	public static final native int bar();\n" + 
2425
		"}\n"
2426
	);
2427
}
2428
public void testBug293300_wksp_07() {
2429
	String source = 
2430
		"package wksp2;\n" + 
2431
		"\n" + 
2432
		"public class X07 {\n" + 
2433
		"	void foo(boolean test) {\n" + 
2434
		"		if (test) {\n" + 
2435
		"			while (true) {\n" + 
2436
		"				try {\n" + 
2437
		"					try {\n" + 
2438
		"					} finally {\n" + 
2439
		"						if (true) {\n" + 
2440
		"							try {\n" + 
2441
		"								toString();\n" + 
2442
		"							} catch (Exception e) {\n" + 
2443
		"							} // nothing\n" + 
2444
		"						}\n" + 
2445
		"					} // first comment which does not move\n" + 
2446
		"\n" + 
2447
		"					// second comment which should not move\n" + 
2448
		"					toString();\n" + 
2449
		"				} catch (Exception e) {\n" + 
2450
		"				}\n" + 
2451
		"\n" + 
2452
		"			} // last comment\n" + 
2453
		"\n" + 
2454
		"		}\n" + 
2455
		"\n" + 
2456
		"		return;\n" + 
2457
		"	}\n" + 
2458
		"}\n";
2459
	formatSource(source);
2460
}
2461
public void testBug293300_wksp2_08() {
2462
	String source = 
2463
		"package wksp2;\n" + 
2464
		"\n" + 
2465
		"public class X08 {\n" + 
2466
		"int foo(int x) {\n" + 
2467
		"    while (x < 0) {\n" + 
2468
		"        switch (x) {\n" + 
2469
		"        \n" + 
2470
		"        }\n" + 
2471
		"    } // end while\n" + 
2472
		"\n" + 
2473
		"        // fill in output parameter\n" + 
2474
		"    if(x > 10)\n" + 
2475
		"        x = 1;\n" + 
2476
		"\n" + 
2477
		"        // return the value\n" + 
2478
		"    return x;\n" + 
2479
		"    }\n" + 
2480
		"}\n";
2481
	formatSource(source,
2482
		"package wksp2;\n" + 
2483
		"\n" + 
2484
		"public class X08 {\n" + 
2485
		"	int foo(int x) {\n" + 
2486
		"		while (x < 0) {\n" + 
2487
		"			switch (x) {\n" + 
2488
		"\n" + 
2489
		"			}\n" + 
2490
		"		} // end while\n" + 
2491
		"\n" + 
2492
		"		// fill in output parameter\n" + 
2493
		"		if (x > 10)\n" + 
2494
		"			x = 1;\n" + 
2495
		"\n" + 
2496
		"		// return the value\n" + 
2497
		"		return x;\n" + 
2498
		"	}\n" + 
2499
		"}\n"
2500
	);
2501
}
2502
public void testBug293300_wksp2_08b() {
2503
	String source = 
2504
		"package wksp2;\n" + 
2505
		"\n" + 
2506
		"public class X08 {\n" + 
2507
		"int foo(int x) {\n" + 
2508
		"    while (x < 0) {\n" + 
2509
		"        switch (x) {\n" + 
2510
		"        \n" + 
2511
		"        }\n" + 
2512
		"    } /* end while */\n" + 
2513
		"\n" + 
2514
		"        // fill in output parameter\n" + 
2515
		"    if(x > 10)\n" + 
2516
		"        x = 1;\n" + 
2517
		"\n" + 
2518
		"        // return the value\n" + 
2519
		"    return x;\n" + 
2520
		"    }\n" + 
2521
		"}\n";
2522
	formatSource(source,
2523
		"package wksp2;\n" + 
2524
		"\n" + 
2525
		"public class X08 {\n" + 
2526
		"	int foo(int x) {\n" + 
2527
		"		while (x < 0) {\n" + 
2528
		"			switch (x) {\n" + 
2529
		"\n" + 
2530
		"			}\n" + 
2531
		"		} /* end while */\n" + 
2532
		"\n" + 
2533
		"		// fill in output parameter\n" + 
2534
		"		if (x > 10)\n" + 
2535
		"			x = 1;\n" + 
2536
		"\n" + 
2537
		"		// return the value\n" + 
2538
		"		return x;\n" + 
2539
		"	}\n" + 
2540
		"}\n"
2541
	);
2542
}
2543
public void testBug293300_wksp2_08c() {
2544
	String source = 
2545
		"package wksp2;\n" + 
2546
		"\n" + 
2547
		"public class X08 {\n" + 
2548
		"int foo(int x) {\n" + 
2549
		"    while (x < 0) {\n" + 
2550
		"        switch (x) {\n" + 
2551
		"        \n" + 
2552
		"        }\n" + 
2553
		"    } /** end while */\n" + 
2554
		"\n" + 
2555
		"        // fill in output parameter\n" + 
2556
		"    if(x > 10)\n" + 
2557
		"        x = 1;\n" + 
2558
		"\n" + 
2559
		"        // return the value\n" + 
2560
		"    return x;\n" + 
2561
		"    }\n" + 
2562
		"}\n";
2563
	formatSource(source,
2564
		"package wksp2;\n" + 
2565
		"\n" + 
2566
		"public class X08 {\n" + 
2567
		"	int foo(int x) {\n" + 
2568
		"		while (x < 0) {\n" + 
2569
		"			switch (x) {\n" + 
2570
		"\n" + 
2571
		"			}\n" + 
2572
		"		}\n" + 
2573
		"		/** end while */\n" + 
2574
		"\n" + 
2575
		"		// fill in output parameter\n" + 
2576
		"		if (x > 10)\n" + 
2577
		"			x = 1;\n" + 
2578
		"\n" + 
2579
		"		// return the value\n" + 
2580
		"		return x;\n" + 
2581
		"	}\n" + 
2582
		"}\n"
2583
	);
2584
}
2585
public void testBug293300_wksp2_09() {
2586
	String source = 
2587
		"package wksp2;\n" + 
2588
		"\n" + 
2589
		"public class X09 {\n" + 
2590
		"void foo(int param) {\n" + 
2591
		"        int local = param - 10000; // first comment\n" + 
2592
		"                                    // on several lines\n" + 
2593
		"        // following unrelated comment\n" + 
2594
		"        // also on several lines\n" + 
2595
		"        int value = param + 10000;\n" + 
2596
		"}\n" + 
2597
		"}\n";
2598
	formatSource(source,
2599
		"package wksp2;\n" + 
2600
		"\n" + 
2601
		"public class X09 {\n" + 
2602
		"	void foo(int param) {\n" + 
2603
		"		int local = param - 10000; // first comment\n" + 
2604
		"									// on several lines\n" + 
2605
		"		// following unrelated comment\n" + 
2606
		"		// also on several lines\n" + 
2607
		"		int value = param + 10000;\n" + 
2608
		"	}\n" + 
2609
		"}\n"
2610
	);
2611
}
2612
public void testBug293300_wksp2_10() {
2613
	String source = 
2614
		"package wksp2;\n" + 
2615
		"\n" + 
2616
		"public class X10 {\n" + 
2617
		"\n" + 
2618
		"    private  String           field;          //  Trailing comment of the field\n" + 
2619
		"                                               //  This comment was not well formatted\n" + 
2620
		"                                               //  as an unexpected line was inserted after the first one\n" + 
2621
		"\n" + 
2622
		"    // -------------------------------\n" + 
2623
		"    X10()  {}\n" + 
2624
		"}\n";
2625
	formatSource(source,
2626
		"package wksp2;\n" + 
2627
		"\n" + 
2628
		"public class X10 {\n" + 
2629
		"\n" + 
2630
		"	private String field; // Trailing comment of the field\n" + 
2631
		"							// This comment was not well formatted\n" + 
2632
		"							// as an unexpected line was inserted after the\n" + 
2633
		"							// first one\n" + 
2634
		"\n" + 
2635
		"	// -------------------------------\n" + 
2636
		"	X10() {\n" + 
2637
		"	}\n" + 
2638
		"}\n"
2639
	);
2640
}
2641
public void testBug293300_wksp2_11() {
2642
	String source = 
2643
		"package wksp2;\n" + 
2644
		"\n" + 
2645
		"public abstract class X11 {\n" + 
2646
		"\n" + 
2647
		"    // [NEW] \n" + 
2648
		"    /**\n" + 
2649
		"     * Comment foo\n" + 
2650
		"     */\n" + 
2651
		"    public abstract StringBuffer foo();\n" + 
2652
		"//#if defined(TEST)\n" + 
2653
		"//#else\n" + 
2654
		"//#endif\n" + 
2655
		"\n" + 
2656
		"    // [NEW]\n" + 
2657
		"    /**\n" + 
2658
		"     * Comment foo2\n" + 
2659
		"     */\n" + 
2660
		"    public abstract StringBuffer foo2();\n" + 
2661
		"    // [NEW]\n" + 
2662
		"    /**\n" + 
2663
		"     * Comment foo3\n" + 
2664
		"     */\n" + 
2665
		"    public abstract StringBuffer foo3();\n" + 
2666
		"\n" + 
2667
		"}\n";
2668
	formatSource(source,
2669
		"package wksp2;\n" + 
2670
		"\n" + 
2671
		"public abstract class X11 {\n" + 
2672
		"\n" + 
2673
		"	// [NEW]\n" + 
2674
		"	/**\n" + 
2675
		"	 * Comment foo\n" + 
2676
		"	 */\n" + 
2677
		"	public abstract StringBuffer foo();\n" + 
2678
		"\n" + 
2679
		"	// #if defined(TEST)\n" + 
2680
		"	// #else\n" + 
2681
		"	// #endif\n" + 
2682
		"\n" + 
2683
		"	// [NEW]\n" + 
2684
		"	/**\n" + 
2685
		"	 * Comment foo2\n" + 
2686
		"	 */\n" + 
2687
		"	public abstract StringBuffer foo2();\n" + 
2688
		"\n" + 
2689
		"	// [NEW]\n" + 
2690
		"	/**\n" + 
2691
		"	 * Comment foo3\n" + 
2692
		"	 */\n" + 
2693
		"	public abstract StringBuffer foo3();\n" + 
2694
		"\n" + 
2695
		"}\n"
2696
	);
2697
}
2698
public void testBug293300_wksp2_12a() {
2699
	String source = 
2700
		"package wksp2;\n" + 
2701
		"\n" + 
2702
		"public class X12 {\n" + 
2703
		"\n" + 
2704
		"\n" + 
2705
		"	private boolean sampleField = false;   //trailing comment of the field which\n" + 
2706
		" 	                                      //was wrongly formatted in previous\n" + 
2707
		"	                                      //version as an unexpected empty lines was\n" + 
2708
		"	                                      //inserted after the second comment line...\n" + 
2709
		"\n" + 
2710
		"\n" + 
2711
		"	/**\n" + 
2712
		"	    Javadoc comment\n" + 
2713
		"	*/\n" + 
2714
		"	public X12() {}\n" + 
2715
		"}\n";
2716
	formatSource(source,
2717
		"package wksp2;\n" + 
2718
		"\n" + 
2719
		"public class X12 {\n" + 
2720
		"\n" + 
2721
		"	private boolean sampleField = false; // trailing comment of the field which\n" + 
2722
		"											// was wrongly formatted in previous\n" + 
2723
		"											// version as an unexpected empty\n" + 
2724
		"											// lines was\n" + 
2725
		"											// inserted after the second comment\n" + 
2726
		"											// line...\n" + 
2727
		"\n" + 
2728
		"	/**\n" + 
2729
		"	 * Javadoc comment\n" + 
2730
		"	 */\n" + 
2731
		"	public X12() {\n" + 
2732
		"	}\n" + 
2733
		"}\n"
2734
	);
2735
}
2736
public void testBug293300_wksp2_12b() {
2737
	String source = 
2738
		"package wksp2;\n" + 
2739
		"\n" + 
2740
		"public class X12 {\n" + 
2741
		"\n" + 
2742
		"\n" + 
2743
		"	private boolean sampleField = false;   //trailing comment of the field which\n" + 
2744
		" 	                                       //was wrongly formatted in previous\n" + 
2745
		"	                                       //version as an unexpected empty lines was\n" + 
2746
		"	                                       //inserted after the second comment line...\n" + 
2747
		"\n" + 
2748
		"\n" + 
2749
		"	/**\n" + 
2750
		"	    Javadoc comment\n" + 
2751
		"	*/\n" + 
2752
		"	public X12() {}\n" + 
2753
		"}\n";
2754
	formatSource(source,
2755
		"package wksp2;\n" + 
2756
		"\n" + 
2757
		"public class X12 {\n" + 
2758
		"\n" + 
2759
		"	private boolean sampleField = false; // trailing comment of the field which\n" + 
2760
		"											// was wrongly formatted in previous\n" + 
2761
		"											// version as an unexpected empty\n" + 
2762
		"											// lines was\n" + 
2763
		"											// inserted after the second comment\n" + 
2764
		"											// line...\n" + 
2765
		"\n" + 
2766
		"	/**\n" + 
2767
		"	 * Javadoc comment\n" + 
2768
		"	 */\n" + 
2769
		"	public X12() {\n" + 
2770
		"	}\n" + 
2771
		"}\n"
2772
	);
2773
}
2774
public void testBug293300_wksp2_13() {
2775
	String source = 
2776
		"package wksp2;\n" + 
2777
		"\n" + 
2778
		"public class X13 {\n" + 
2779
		"void foo(int x) {\n" + 
2780
		"	switch (x) {\n" + 
2781
		"		default : // regular object ref\n" + 
2782
		"//				if (compileTimeType.isRawType() && runtimeTimeType.isBoundParameterizedType()) {\n" + 
2783
		"//				    scope.problemReporter().unsafeRawExpression(this, compileTimeType, runtimeTimeType);\n" + 
2784
		"//				}\n" + 
2785
		"	}\n" + 
2786
		"}\n" + 
2787
		"}\n";
2788
	formatSource(source,
2789
		"package wksp2;\n" + 
2790
		"\n" + 
2791
		"public class X13 {\n" + 
2792
		"	void foo(int x) {\n" + 
2793
		"		switch (x) {\n" + 
2794
		"		default: // regular object ref\n" + 
2795
		"			// if (compileTimeType.isRawType() &&\n" + 
2796
		"			// runtimeTimeType.isBoundParameterizedType()) {\n" + 
2797
		"			// scope.problemReporter().unsafeRawExpression(this,\n" + 
2798
		"			// compileTimeType, runtimeTimeType);\n" + 
2799
		"			// }\n" + 
2800
		"		}\n" + 
2801
		"	}\n" + 
2802
		"}\n"
2803
	);
2804
}
2805
public void testBug293300_wksp2_14() {
2806
	String source = 
2807
		"package wksp2;\n" + 
2808
		"\n" + 
2809
		"public interface X14 {\n" + 
2810
		"void foo();\n" + 
2811
		"// line 1\n" + 
2812
		"// line 2\n" + 
2813
		"void bar();\n" + 
2814
		"}\n";
2815
	formatSource(source,
2816
		"package wksp2;\n" + 
2817
		"\n" + 
2818
		"public interface X14 {\n" + 
2819
		"	void foo();\n" + 
2820
		"\n" + 
2821
		"	// line 1\n" + 
2822
		"	// line 2\n" + 
2823
		"	void bar();\n" + 
2824
		"}\n"
2825
	);
2826
}
2827
// TODO (frederic) try to fix the formatter instability in the following test case
2828
public void _testBug293300_wksp2_15a() {
2829
	String source = 
2830
		"package wksp2;\n" + 
2831
		"\n" + 
2832
		"public class X15 {\n" + 
2833
		"	void foo(int[] params) {\n" + 
2834
		"		if (params.length > 0) { // trailing comment formatted in several lines...\n" + 
2835
		"//			int length = params == null ? : 0 params.length; // this commented lined causes troubles for the formatter but only if the comment starts at column 1...\n" + 
2836
		"			for (int i=0; i<params.length; i++) {\n" + 
2837
		"			}\n" + 
2838
		"		}\n" + 
2839
		"	}\n" + 
2840
		"}\n";
2841
	formatSource(source,
2842
		"\n" + 
2843
		"public class X15 {\n" + 
2844
		"	void foo(int[] params) {\n" + 
2845
		"		if (params.length > 0) { // trailing comment formatted in several\n" + 
2846
		"									// lines...\n" + 
2847
		"			// int length = params == null ? : 0 params.length; // this\n" + 
2848
		"			// commented\n" + 
2849
		"			// lined causes troubles for the formatter but only if the comment\n" + 
2850
		"			// starts at column 1...\n" + 
2851
		"			for (int i = 0; i < params.length; i++) {\n" + 
2852
		"			}\n" + 
2853
		"		}\n" + 
2854
		"	}\n" + 
2855
		"}\n"
2856
	);
2857
}
2858
public void testBug293300_wksp2_15b() {
2859
	String source = 
2860
		"package wksp2;\n" + 
2861
		"\n" + 
2862
		"public class X15 {\n" + 
2863
		"	void foo(int[] params) {\n" + 
2864
		"		if (params.length > 0) { // trailing comment formatted in several lines...\n" + 
2865
		"			// int length = params == null ? : 0 params.length; // this commented lined does not cause troubles for the formatter when the comments is not on column 1...\n" + 
2866
		"			for (int i=0; i<params.length; i++) {\n" + 
2867
		"			}\n" + 
2868
		"		}\n" + 
2869
		"	}\n" + 
2870
		"}\n";
2871
	formatSource(source,
2872
		"package wksp2;\n" + 
2873
		"\n" + 
2874
		"public class X15 {\n" + 
2875
		"	void foo(int[] params) {\n" + 
2876
		"		if (params.length > 0) { // trailing comment formatted in several\n" + 
2877
		"									// lines...\n" + 
2878
		"			// int length = params == null ? : 0 params.length; // this\n" + 
2879
		"			// commented lined does not cause troubles for the formatter when\n" + 
2880
		"			// the comments is not on column 1...\n" + 
2881
		"			for (int i = 0; i < params.length; i++) {\n" + 
2882
		"			}\n" + 
2883
		"		}\n" + 
2884
		"	}\n" + 
2885
		"}\n"
2886
	);
2887
}
2888
public void testBug293300_wksp3_01() {
2889
	String source = 
2890
		"package wksp3;\n" + 
2891
		"\n" + 
2892
		"public class X01 {\n" + 
2893
		"static String[] constant = {\n" + 
2894
		"// comment\n" + 
2895
		"\"first\",\n" + 
2896
		"// comment\n" + 
2897
		"\"second\",\n" + 
2898
		"};\n" + 
2899
		"}\n";
2900
	formatSource(source,
2901
		"package wksp3;\n" + 
2902
		"\n" + 
2903
		"public class X01 {\n" + 
2904
		"	static String[] constant = {\n" + 
2905
		"			// comment\n" + 
2906
		"			\"first\",\n" + 
2907
		"			// comment\n" + 
2908
		"			\"second\", };\n" + 
2909
		"}\n"
2910
	);
2911
}
2912
2913
/**
1558
 * @bug 293496:  [formatter] 'insert_space_before_opening_brace_in_array_initializer' preference may be reset in certain circumstances
2914
 * @bug 293496:  [formatter] 'insert_space_before_opening_brace_in_array_initializer' preference may be reset in certain circumstances
1559
 * @test Verify that non ArithmeticException occurs when using tab size = 0
2915
 * @test Verify that non ArithmeticException occurs when using tab size = 0
1560
 * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=293496"
2916
 * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=293496"
(-)src/org/eclipse/jdt/core/tests/formatter/FormatterMassiveRegressionTests.java (-1 / +12 lines)
Lines 273-278 Link Here
273
	private static String ECLIPSE_MILESTONE;
273
	private static String ECLIPSE_MILESTONE;
274
	private static String JDT_CORE_VERSION;
274
	private static String JDT_CORE_VERSION;
275
	private static String PATCH_BUG, PATCH_VERSION;
275
	private static String PATCH_BUG, PATCH_VERSION;
276
	private static String TEMP_OUTPUT;
276
	private static boolean JDT_CORE_HEAD;
277
	private static boolean JDT_CORE_HEAD;
277
	private final static IPath[] EXPECTED_FAILURES = INPUT_DIR.getPath().indexOf("v34") < 0
278
	private final static IPath[] EXPECTED_FAILURES = INPUT_DIR.getPath().indexOf("v34") < 0
278
		? new IPath[] {
279
		? new IPath[] {
Lines 479-489 Link Here
479
			String token = tokenizer.nextToken();
480
			String token = tokenizer.nextToken();
480
			if (token.equals("clean")) {
481
			if (token.equals("clean")) {
481
				CLEAN = true;
482
				CLEAN = true;
483
			} else if (token.equals("tmp")) {
484
				TEMP_OUTPUT = PATCH_BUG;
482
			}
485
			}
483
		}
486
		}
484
		setOutputDir(outputDir, buffer);
487
		setOutputDir(outputDir, buffer);
485
		if (CLEAN) {
488
		if (CLEAN) {
486
			if (PATCH_BUG != null || JDT_CORE_HEAD) {
489
			if (TEMP_OUTPUT == null && (PATCH_BUG != null || JDT_CORE_HEAD)) {
487
				System.err.println("Reference can only be updated using a version (i.e. with a closed buildnotes_jdt-core.html)!");
490
				System.err.println("Reference can only be updated using a version (i.e. with a closed buildnotes_jdt-core.html)!");
488
				System.exit(1);
491
				System.exit(1);
489
			}
492
			}
Lines 542-547 Link Here
542
	if (PATCH_BUG != null) {
545
	if (PATCH_BUG != null) {
543
		logDir = new File(logDir, "tests");
546
		logDir = new File(logDir, "tests");
544
		logDir = new File(logDir, PATCH_BUG);
547
		logDir = new File(logDir, PATCH_BUG);
548
		if (TEMP_OUTPUT != null) {
549
			logDir = new File(logDir, "tmp");
550
		}
545
		logDir = new File(logDir, PATCH_VERSION);
551
		logDir = new File(logDir, PATCH_VERSION);
546
//		folder = folder.getFolder("tests");
552
//		folder = folder.getFolder("tests");
547
//		if (!folder.exists()) folder.create(true, true, null);
553
//		if (!folder.exists()) folder.create(true, true, null);
Lines 635-640 Link Here
635
	if (OUTPUT_DIR.getName().equals(ECLIPSE_VERSION)) {
641
	if (OUTPUT_DIR.getName().equals(ECLIPSE_VERSION)) {
636
		OUTPUT_DIR = OUTPUT_DIR.getParentFile();
642
		OUTPUT_DIR = OUTPUT_DIR.getParentFile();
637
	}
643
	}
644
	
645
	// Add the temporary output if any
646
	if (TEMP_OUTPUT != null) {
647
		OUTPUT_DIR = new File(OUTPUT_DIR, TEMP_OUTPUT);
648
	}
638
649
639
	// Compute output sub-directories depending on profiles
650
	// Compute output sub-directories depending on profiles
640
	if (NO_COMMENTS || BRACES != null || JOIN_LINES != null) {
651
	if (NO_COMMENTS || BRACES != null || JOIN_LINES != null) {

Return to bug 293300