Java Code Examples for org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants#JDK1_3

The following examples show how to use org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants#JDK1_3 . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: DocCommentParser.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 6 votes vote down vote up
DocCommentParser(AST ast, Scanner scanner, boolean check) {
	super(null);
	this.ast = ast;
	this.scanner = scanner;
	switch(this.ast.apiLevel()) {
		case AST.JLS2_INTERNAL :
			this.sourceLevel = ClassFileConstants.JDK1_3;
			break;
		case AST.JLS3_INTERNAL:
			this.sourceLevel = ClassFileConstants.JDK1_5;
			break;
		default:
			// AST.JLS4 for now
			this.sourceLevel = ClassFileConstants.JDK1_7;
	}
	this.checkDocComment = check;
	this.kind = DOM_PARSER | TEXT_PARSE;
}
 
Example 2
Source File: AbstractCommentParser.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 6 votes vote down vote up
protected AbstractCommentParser(Parser sourceParser) {
	this.sourceParser = sourceParser;
	this.scanner = new Scanner(false, false, false, ClassFileConstants.JDK1_3, null, null, true/*taskCaseSensitive*/);
	this.identifierStack = new char[20][];
	this.identifierPositionStack = new long[20];
	this.identifierLengthStack = new int[10];
	this.astStack = new Object[30];
	this.astLengthStack = new int[20];
	this.reportProblems = sourceParser != null;
	if (sourceParser != null) {
		this.checkDocComment = this.sourceParser.options.docCommentSupport;
		this.sourceLevel = this.sourceParser.options.sourceLevel;
		this.scanner.sourceLevel = this.sourceLevel;
		this.complianceLevel = this.sourceParser.options.complianceLevel;
	}
}
 
Example 3
Source File: SimpleName.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 5 votes vote down vote up
/**
 * Sets the identifier of this node to the given value.
 * The identifier should be legal according to the rules
 * of the Java language. Note that keywords are not legal
 * identifiers.
 * <p>
 * Note that the list of keywords may depend on the version of the
 * language (determined when the AST object was created).
 * </p>
 *
 * @param identifier the identifier of this node
 * @exception IllegalArgumentException if the identifier is invalid
 */
public void setIdentifier(String identifier) {
	// update internalSetIdentifier if this is changed
	if (identifier == null) {
		throw new IllegalArgumentException();
	}
	Scanner scanner = this.ast.scanner;
	long sourceLevel = scanner.sourceLevel;
	long complianceLevel = scanner.complianceLevel;

	try {
		scanner.sourceLevel = ClassFileConstants.JDK1_3;
		scanner.complianceLevel = ClassFileConstants.JDK1_5;
		char[] source = identifier.toCharArray();
		scanner.setSource(source);
		final int length = source.length;
		scanner.resetTo(0, length - 1);
		try {
			int tokenType = scanner.scanIdentifier();
			if (tokenType != TerminalTokens.TokenNameIdentifier) {
				throw new IllegalArgumentException("Invalid identifier : >" + identifier + "<");  //$NON-NLS-1$//$NON-NLS-2$
			}
			if (scanner.currentPosition != length) {
				// this is the case when there is only one identifier see 87849
				throw new IllegalArgumentException("Invalid identifier : >" + identifier + "<");  //$NON-NLS-1$//$NON-NLS-2$
			}
		} catch (InvalidInputException e) {
			IllegalArgumentException iae = new IllegalArgumentException("Invalid identifier : >" + identifier + "<"); //$NON-NLS-1$//$NON-NLS-2$
			iae.initCause(e);
			throw iae; 
		}
	} finally {
		this.ast.scanner.sourceLevel = sourceLevel;
		this.ast.scanner.complianceLevel = complianceLevel;
	}
	preValueChange(IDENTIFIER_PROPERTY);
	this.identifier = identifier;
	postValueChange(IDENTIFIER_PROPERTY);
}
 
Example 4
Source File: AST.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 5 votes vote down vote up
/**
 * Creates a new, empty abstract syntax tree using the given options.
 * <p>
 * Following option keys are significant:
 * <ul>
 * <li><code>"org.eclipse.jdt.core.compiler.source"</code> -
 *    indicates source compatibility mode (as per <code>JavaCore</code>);
 *    <code>"1.3"</code> means the source code is as per JDK 1.3;
 *    <code>"1.4"</code> means the source code is as per JDK 1.4
 *    (<code>"assert"</code> is now a keyword);
 *    <code>"1.5"</code> means the source code is as per JDK 1.5
 *    (<code>"enum"</code> is now a keyword);
 *    <code>"1.7"</code> means the source code is as per JDK 1.7;
 *    additional legal values may be added later. </li>
 * </ul>
 * Options other than the above are ignored.
 * </p>
 *
 * @param options the table of options (key type: <code>String</code>;
 *    value type: <code>String</code>)
 * @see JavaCore#getDefaultOptions()
 * @deprecated Clients should port their code to use the new JLS4 AST API and call
 *    {@link #newAST(int) AST.newAST(AST.JLS4)} instead of using this constructor.
 */
public AST(Map options) {
	this(JLS2);
	Object sourceLevelOption = options.get(JavaCore.COMPILER_SOURCE);
	long sourceLevel = ClassFileConstants.JDK1_3;
	if (JavaCore.VERSION_1_4.equals(sourceLevelOption)) {
		sourceLevel = ClassFileConstants.JDK1_4;
	} else if (JavaCore.VERSION_1_5.equals(sourceLevelOption)) {
		sourceLevel = ClassFileConstants.JDK1_5;
	} else if (JavaCore.VERSION_1_7.equals(sourceLevelOption)) {
		sourceLevel = ClassFileConstants.JDK1_7;
	}
	Object complianceLevelOption = options.get(JavaCore.COMPILER_COMPLIANCE);
	long complianceLevel = ClassFileConstants.JDK1_3;
	if (JavaCore.VERSION_1_4.equals(complianceLevelOption)) {
		complianceLevel = ClassFileConstants.JDK1_4;
	} else if (JavaCore.VERSION_1_5.equals(complianceLevelOption)) {
		complianceLevel = ClassFileConstants.JDK1_5;
	} else if (JavaCore.VERSION_1_7.equals(complianceLevelOption)) {
		complianceLevel = ClassFileConstants.JDK1_7;
	}
	// override scanner if 1.4 or 1.5 asked for
	this.scanner = new Scanner(
		true /*comment*/,
		true /*whitespace*/,
		false /*nls*/,
		sourceLevel /*sourceLevel*/,
		complianceLevel /*complianceLevel*/,
		null/*taskTag*/,
		null/*taskPriorities*/,
		true/*taskCaseSensitive*/);
}
 
Example 5
Source File: ThrowStatement.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 5 votes vote down vote up
public void resolve(BlockScope scope) {
	this.exceptionType = this.exception.resolveType(scope);
	recordExceptionsForEnclosingLambda(scope, this.exceptionType);
	if (this.exceptionType != null && this.exceptionType.isValidBinding()) {
		if (this.exceptionType == TypeBinding.NULL) {
			if (scope.compilerOptions().complianceLevel <= ClassFileConstants.JDK1_3){
				// if compliant with 1.4, this problem will not be reported
				scope.problemReporter().cannotThrowNull(this.exception);
			}
	 	} else if (this.exceptionType.findSuperTypeOriginatingFrom(TypeIds.T_JavaLangThrowable, true) == null) {
			scope.problemReporter().cannotThrowType(this.exception, this.exceptionType);
		}
		this.exception.computeConversion(scope, this.exceptionType, this.exceptionType);
	}
}
 
Example 6
Source File: CompilerOptions.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 5 votes vote down vote up
public static String versionFromJdkLevel(long jdkLevel) {
	switch ((int)(jdkLevel>>16)) {
		case ClassFileConstants.MAJOR_VERSION_1_1 :
			if (jdkLevel == ClassFileConstants.JDK1_1)
				return VERSION_1_1;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_2 :
			if (jdkLevel == ClassFileConstants.JDK1_2)
				return VERSION_1_2;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_3 :
			if (jdkLevel == ClassFileConstants.JDK1_3)
				return VERSION_1_3;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_4 :
			if (jdkLevel == ClassFileConstants.JDK1_4)
				return VERSION_1_4;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_5 :
			if (jdkLevel == ClassFileConstants.JDK1_5)
				return VERSION_1_5;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_6 :
			if (jdkLevel == ClassFileConstants.JDK1_6)
				return VERSION_1_6;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_7 :
			if (jdkLevel == ClassFileConstants.JDK1_7)
				return VERSION_1_7;
			break;
		case ClassFileConstants.MAJOR_VERSION_1_8 :
			if (jdkLevel == ClassFileConstants.JDK1_8)
				return VERSION_1_8;
			break;
	}
	return Util.EMPTY_STRING; // unknown version
}
 
Example 7
Source File: CompilerOptions.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 5 votes vote down vote up
public static long versionToJdkLevel(Object versionID) {
	if (versionID instanceof String) {
		String version = (String) versionID;
		// verification is optimized for all versions with same length and same "1." prefix
		if (version.length() == 3 && version.charAt(0) == '1' && version.charAt(1) == '.') {
			switch (version.charAt(2)) {
				case '1':
					return ClassFileConstants.JDK1_1;
				case '2':
					return ClassFileConstants.JDK1_2;
				case '3':
					return ClassFileConstants.JDK1_3;
				case '4':
					return ClassFileConstants.JDK1_4;
				case '5':
					return ClassFileConstants.JDK1_5;
				case '6':
					return ClassFileConstants.JDK1_6;
				case '7':
					return ClassFileConstants.JDK1_7;
				case '8':
					return ClassFileConstants.JDK1_8;
				default:
					return 0; // unknown
			}
		}
		if (VERSION_JSR14.equals(versionID)) {
			return ClassFileConstants.JDK1_4;
		}
		if (VERSION_CLDC1_1.equals(versionID)) {
			return ClassFileConstants.CLDC_1_1;
		}
	}
	return 0; // unknown
}
 
Example 8
Source File: CompletionJavadocParser.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
public CompletionJavadocParser(CompletionParser sourceParser) {
	super(sourceParser);
	this.scanner = new CompletionScanner(ClassFileConstants.JDK1_3);
	this.kind = COMPLETION_PARSER | TEXT_PARSE;
	initLevelTags();
}
 
Example 9
Source File: PublicScanner.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
public PublicScanner() {
	this(false /*comment*/, false /*whitespace*/, false /*nls*/, ClassFileConstants.JDK1_3 /*sourceLevel*/, null/*taskTag*/, null/*taskPriorities*/, true /*taskCaseSensitive*/);
}
 
Example 10
Source File: ToolFactory.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
/**
 * Create a scanner, indicating the level of detail requested for tokenizing. The scanner can then be
 * used to tokenize some source in a Java aware way.
 * Here is a typical scanning loop:
 *
 * <code>
 * <pre>
 *   IScanner scanner = ToolFactory.createScanner(false, false, false, false);
 *   scanner.setSource("int i = 0;".toCharArray());
 *   while (true) {
 *     int token = scanner.getNextToken();
 *     if (token == ITerminalSymbols.TokenNameEOF) break;
 *     System.out.println(token + " : " + new String(scanner.getCurrentTokenSource()));
 *   }
 * </pre>
 * </code>
 *
 * <p>By default the compliance used to create the scanner is the workspace's compliance when running inside the IDE
 * or 1.4 if running from outside of a headless eclipse.
 * </p>
 *
 * @param tokenizeComments if set to <code>false</code>, comments will be silently consumed
 * @param tokenizeWhiteSpace if set to <code>false</code>, white spaces will be silently consumed,
 * @param assertMode if set to <code>false</code>, occurrences of 'assert' will be reported as identifiers
 * ({@link ITerminalSymbols#TokenNameIdentifier}), whereas if set to <code>true</code>, it
 * would report assert keywords ({@link ITerminalSymbols#TokenNameassert}). Java 1.4 has introduced
 * a new 'assert' keyword.
 * @param recordLineSeparator if set to <code>true</code>, the scanner will record positions of encountered line
 * separator ends. In case of multi-character line separators, the last character position is considered. These positions
 * can then be extracted using {@link IScanner#getLineEnds()}. Only non-unicode escape sequences are
 * considered as valid line separators.
 	 * @return a scanner
 * @see org.eclipse.jdt.core.compiler.IScanner
 * @see #createScanner(boolean, boolean, boolean, String, String)
 */
public static IScanner createScanner(boolean tokenizeComments, boolean tokenizeWhiteSpace, boolean assertMode, boolean recordLineSeparator){
	// use default workspace compliance
	long complianceLevelValue = CompilerOptions.versionToJdkLevel(JavaCore.getOption(JavaCore.COMPILER_COMPLIANCE));
	if (complianceLevelValue == 0) complianceLevelValue = ClassFileConstants.JDK1_4; // fault-tolerance
	PublicScanner scanner =
		new PublicScanner(
			tokenizeComments,
			tokenizeWhiteSpace,
			false/*nls*/,
			assertMode ? ClassFileConstants.JDK1_4 : ClassFileConstants.JDK1_3/*sourceLevel*/,
			complianceLevelValue,
			null/*taskTags*/,
			null/*taskPriorities*/,
			true/*taskCaseSensitive*/);
	scanner.recordLineSeparator = recordLineSeparator;
	return scanner;
}
 
Example 11
Source File: ToolFactory.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
/**
 * Create a scanner, indicating the level of detail requested for tokenizing. The scanner can then be
 * used to tokenize some source in a Java aware way.
 * Here is a typical scanning loop:
 *
 * <code>
 * <pre>
 *   IScanner scanner = ToolFactory.createScanner(false, false, false, false);
 *   scanner.setSource("int i = 0;".toCharArray());
 *   while (true) {
 *     int token = scanner.getNextToken();
 *     if (token == ITerminalSymbols.TokenNameEOF) break;
 *     System.out.println(token + " : " + new String(scanner.getCurrentTokenSource()));
 *   }
 * </pre>
 * </code>
 *
 * <p>By default the compliance used to create the scanner is the workspace's compliance when running inside the IDE
 * or 1.4 if running from outside of a headless eclipse.
 * </p>
 *
 * @param tokenizeComments if set to <code>false</code>, comments will be silently consumed
 * @param tokenizeWhiteSpace if set to <code>false</code>, white spaces will be silently consumed,
 * @param recordLineSeparator if set to <code>true</code>, the scanner will record positions of encountered line
 * separator ends. In case of multi-character line separators, the last character position is considered. These positions
 * can then be extracted using {@link IScanner#getLineEnds()}. Only non-unicode escape sequences are
 * considered as valid line separators.
 * @param sourceLevel if set to <code>&quot;1.3&quot;</code> or <code>null</code>, occurrences of 'assert' will be reported as identifiers
 * ({@link ITerminalSymbols#TokenNameIdentifier}), whereas if set to <code>&quot;1.4&quot;</code>, it
 * would report assert keywords ({@link ITerminalSymbols#TokenNameassert}). Java 1.4 has introduced
 * a new 'assert' keyword.
 * @return a scanner
 * @see org.eclipse.jdt.core.compiler.IScanner
 * @see #createScanner(boolean, boolean, boolean, String, String)
 * @since 3.0
 */
public static IScanner createScanner(boolean tokenizeComments, boolean tokenizeWhiteSpace, boolean recordLineSeparator, String sourceLevel) {
	// use default workspace compliance
	long complianceLevelValue = CompilerOptions.versionToJdkLevel(JavaCore.getOption(JavaCore.COMPILER_COMPLIANCE));
	if (complianceLevelValue == 0) complianceLevelValue = ClassFileConstants.JDK1_4; // fault-tolerance
	long sourceLevelValue = CompilerOptions.versionToJdkLevel(sourceLevel);
	if (sourceLevelValue == 0) sourceLevelValue = ClassFileConstants.JDK1_3; // fault-tolerance
	PublicScanner scanner =
		new PublicScanner(
			tokenizeComments,
			tokenizeWhiteSpace,
			false/*nls*/,
			sourceLevelValue /*sourceLevel*/,
			complianceLevelValue,
			null/*taskTags*/,
			null/*taskPriorities*/,
			true/*taskCaseSensitive*/);
	scanner.recordLineSeparator = recordLineSeparator;
	return scanner;
}
 
Example 12
Source File: AST.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
/**
 * Creates a new Java abstract syntax tree
    * (AST) following the specified set of API rules.
    *
	 * @param level the API level; one of the <code>JLS*</code> level constants
    * @since 3.0
 */
private AST(int level) {
	switch(level) {
		case JLS2_INTERNAL :
		case JLS3_INTERNAL :
			this.apiLevel = level;
			// initialize a scanner
			this.scanner = new Scanner(
					true /*comment*/,
					true /*whitespace*/,
					false /*nls*/,
					ClassFileConstants.JDK1_3 /*sourceLevel*/,
					ClassFileConstants.JDK1_5 /*complianceLevel*/,
					null/*taskTag*/,
					null/*taskPriorities*/,
					true/*taskCaseSensitive*/);
			break;
		case JLS4_INTERNAL :
			this.apiLevel = level;
			// initialize a scanner
			this.scanner = new Scanner(
					true /*comment*/,
					true /*whitespace*/,
					false /*nls*/,
					ClassFileConstants.JDK1_7 /*sourceLevel*/,
					ClassFileConstants.JDK1_7 /*complianceLevel*/,
					null/*taskTag*/,
					null/*taskPriorities*/,
					true/*taskCaseSensitive*/);
			break;
		case JLS8 :
			this.apiLevel = level;
			// initialize a scanner
			this.scanner = new Scanner(
					true /*comment*/,
					true /*whitespace*/,
					false /*nls*/,
					ClassFileConstants.JDK1_8 /*sourceLevel*/,
					ClassFileConstants.JDK1_8 /*complianceLevel*/,
					null/*taskTag*/,
					null/*taskPriorities*/,
					true/*taskCaseSensitive*/);
			break;	
		default:
			throw new IllegalArgumentException("Unsupported JLS level"); //$NON-NLS-1$
	}
}
 
Example 13
Source File: Main.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
/**
 * Return true if and only if the running VM supports the given minimal version.
 *
 * <p>This only checks the major version, since the minor version is always 0 (at least for the useful cases).</p>
 * <p>The given minimalSupportedVersion is one of the constants:</p>
 * <ul>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_1</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_2</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_3</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_4</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_5</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_6</code></li>
 * <li><code>org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants.JDK1_7</code></li>
 * </ul>
 * @param minimalSupportedVersion the given minimal version
 * @return true if and only if the running VM supports the given minimal version, false otherwise
 */
private boolean checkVMVersion(long minimalSupportedVersion) {
	// the format of this property is supposed to be xx.x where x are digits.
	String classFileVersion = System.getProperty("java.class.version"); //$NON-NLS-1$
	if (classFileVersion == null) {
		// by default we don't support a class file version we cannot recognize
		return false;
	}
	int index = classFileVersion.indexOf('.');
	if (index == -1) {
		// by default we don't support a class file version we cannot recognize
		return false;
	}
	int majorVersion;
	try {
		majorVersion = Integer.parseInt(classFileVersion.substring(0, index));
	} catch (NumberFormatException e) {
		// by default we don't support a class file version we cannot recognize
		return false;
	}
	switch(majorVersion) {
		case ClassFileConstants.MAJOR_VERSION_1_1 : // 1.0 and 1.1
			return ClassFileConstants.JDK1_1 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_2 : // 1.2
			return ClassFileConstants.JDK1_2 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_3 : // 1.3
			return ClassFileConstants.JDK1_3 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_4 : // 1.4
			return ClassFileConstants.JDK1_4 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_5 : // 1.5
			return ClassFileConstants.JDK1_5 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_6 : // 1.6
			return ClassFileConstants.JDK1_6 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_7 : // 1.7
			return ClassFileConstants.JDK1_7 >= minimalSupportedVersion;
		case ClassFileConstants.MAJOR_VERSION_1_8: // 1.8
			return ClassFileConstants.JDK1_8 >= minimalSupportedVersion;
	}
	// unknown version
	return false;
}
 
Example 14
Source File: Scanner.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
public Scanner() {
	this(false /*comment*/, false /*whitespace*/, false /*nls*/, ClassFileConstants.JDK1_3 /*sourceLevel*/, null/*taskTag*/, null/*taskPriorities*/, true /*taskCaseSensitive*/);
}
 
Example 15
Source File: ForeachStatement.java    From Eclipse-Postfix-Code-Completion with Eclipse Public License 1.0 4 votes vote down vote up
public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, FlowInfo flowInfo) {
	// initialize break and continue labels
	this.breakLabel = new BranchLabel();
	this.continueLabel = new BranchLabel();
	int initialComplaintLevel = (flowInfo.reachMode() & FlowInfo.UNREACHABLE) != 0 ? Statement.COMPLAINED_FAKE_REACHABLE : Statement.NOT_COMPLAINED;

	// process the element variable and collection
	this.collection.checkNPE(currentScope, flowContext, flowInfo);
	flowInfo = this.elementVariable.analyseCode(this.scope, flowContext, flowInfo);		
	FlowInfo condInfo = this.collection.analyseCode(this.scope, flowContext, flowInfo.copy());
	LocalVariableBinding elementVarBinding = this.elementVariable.binding;

	// element variable will be assigned when iterating
	condInfo.markAsDefinitelyAssigned(elementVarBinding);

	this.postCollectionInitStateIndex = currentScope.methodScope().recordInitializationStates(condInfo);


	// process the action
	LoopingFlowContext loopingContext =
		new LoopingFlowContext(flowContext, flowInfo, this, this.breakLabel,
			this.continueLabel, this.scope, true);
	UnconditionalFlowInfo actionInfo =
		condInfo.nullInfoLessUnconditionalCopy();
	actionInfo.markAsDefinitelyUnknown(elementVarBinding);
	if (currentScope.compilerOptions().isAnnotationBasedNullAnalysisEnabled) {
		int elementNullStatus = FlowInfo.tagBitsToNullStatus(this.collectionElementType.tagBits);
		int nullStatus = NullAnnotationMatching.checkAssignment(currentScope, flowContext, elementVarBinding, elementNullStatus,
																	this.collection, this.collectionElementType);
		if ((elementVarBinding.type.tagBits & TagBits.IsBaseType) == 0) {
			actionInfo.markNullStatus(elementVarBinding, nullStatus);
		}
	}
	FlowInfo exitBranch;
	if (!(this.action == null || (this.action.isEmptyBlock()
			&& currentScope.compilerOptions().complianceLevel <= ClassFileConstants.JDK1_3))) {

		if (this.action.complainIfUnreachable(actionInfo, this.scope, initialComplaintLevel, true) < Statement.COMPLAINED_UNREACHABLE) {
			actionInfo = this.action.analyseCode(this.scope, loopingContext, actionInfo).unconditionalCopy();
		}

		// code generation can be optimized when no need to continue in the loop
		exitBranch = flowInfo.unconditionalCopy().
				addInitializationsFrom(condInfo.initsWhenFalse());
		// TODO (maxime) no need to test when false: can optimize (same for action being unreachable above)
		if ((actionInfo.tagBits & loopingContext.initsOnContinue.tagBits &
				FlowInfo.UNREACHABLE_OR_DEAD) != 0) {
			this.continueLabel = null;
		} else {
			actionInfo = actionInfo.mergedWith(loopingContext.initsOnContinue);
			loopingContext.complainOnDeferredFinalChecks(this.scope, actionInfo);
			exitBranch.addPotentialInitializationsFrom(actionInfo);
		}
	} else {
		exitBranch = condInfo.initsWhenFalse();
	}

	// we need the variable to iterate the collection even if the
	// element variable is not used
	final boolean hasEmptyAction = this.action == null
	|| this.action.isEmptyBlock()
	|| ((this.action.bits & IsUsefulEmptyStatement) != 0);

	switch(this.kind) {
		case ARRAY :
			if (!hasEmptyAction
					|| elementVarBinding.resolvedPosition != -1) {
				this.collectionVariable.useFlag = LocalVariableBinding.USED;
				if (this.continueLabel != null) {
					this.indexVariable.useFlag = LocalVariableBinding.USED;
					this.maxVariable.useFlag = LocalVariableBinding.USED;
				}
			}
			break;
		case RAW_ITERABLE :
		case GENERIC_ITERABLE :
			this.indexVariable.useFlag = LocalVariableBinding.USED;
			break;
	}
	//end of loop
	loopingContext.complainOnDeferredNullChecks(currentScope, actionInfo);

	FlowInfo mergedInfo = FlowInfo.mergedOptimizedBranches(
			(loopingContext.initsOnBreak.tagBits &
					FlowInfo.UNREACHABLE) != 0 ?
							loopingContext.initsOnBreak :
								flowInfo.addInitializationsFrom(loopingContext.initsOnBreak), // recover upstream null info
								false,
								exitBranch,
								false,
								true /*for(;;){}while(true); unreachable(); */);
	mergedInfo.resetAssignmentInfo(this.elementVariable.binding);
	this.mergedInitStateIndex = currentScope.methodScope().recordInitializationStates(mergedInfo);
	return mergedInfo;
}