Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPhilipe Mulet2001-10-04 14:32:19 +0000
committerPhilipe Mulet2001-10-04 14:32:19 +0000
commitb0ab1df1b7826540b50bedb32e27cbe41107ea88 (patch)
tree0cc305751524af4f55a4d00454da89323e56dae2
parent91528d6a3c03fe2ac3f37d4a1dd477d6a256d916 (diff)
downloadeclipse.jdt.core-unlabeled-1.6.2.tar.gz
eclipse.jdt.core-unlabeled-1.6.2.tar.xz
eclipse.jdt.core-unlabeled-1.6.2.zip
*** empty log message ***unlabeled-1.6.2
-rw-r--r--org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/ClasspathJar.java21
-rw-r--r--org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/CompilationUnit.java31
-rw-r--r--org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java2
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/DocumentElementParser.java44
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java109
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AstNode.java62
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/BinaryExpression.java26
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Block.java198
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Break.java4
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/CompoundAssignment.java35
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ConstructorDeclaration.java38
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Continue.java4
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/DoStatement.java5
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/IfStatement.java2
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/LabeledStatement.java3
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ReturnStatement.java7
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/TryStatement.java25
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/UnaryExpression.java454
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/ExceptionHandlingFlowContext.java186
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/FlowContext.java662
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LabelFlowContext.java53
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LoopingFlowContext.java181
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/SwitchFlowContext.java57
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/impl/Constant.java6
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/CompilationUnitScope.java4
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java5
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredField.java1
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredInitializer.java2
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredMethod.java1
-rw-r--r--org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/util/Util.java168
-rw-r--r--org.eclipse.jdt.core/eval/org/eclipse/jdt/internal/eval/CodeSnippetParser.java9
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaProject.java12
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Openable.java12
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Util.java81
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/BuildNotifier.java4
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectBinaryOutput.java12
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectResourceCopier.java3
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/hierarchy/TypeHierarchy.java23
-rw-r--r--org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/jdom/SimpleDOMBuilder.java22
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/core/search/SearchEngine.java8
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/FileDocument.java4
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/IFileDocument.java4
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddClassFileToIndex.java2
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddCompilationUnitToIndex.java2
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddJarFileToIndex.java11
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/IIndexConstants.java4
-rw-r--r--org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/SourceIndexer.java2
47 files changed, 1506 insertions, 1105 deletions
diff --git a/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/ClasspathJar.java b/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/ClasspathJar.java
index 70c5634b92..1e8e6b286e 100644
--- a/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/ClasspathJar.java
+++ b/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/ClasspathJar.java
@@ -10,6 +10,7 @@ import java.util.zip.*;
import org.eclipse.jdt.internal.compiler.env.*;
import org.eclipse.jdt.internal.compiler.classfmt.*;
+import org.eclipse.jdt.internal.compiler.util.Util;
class ClasspathJar implements FileSystem.Classpath {
ZipFile zipFile;
@@ -61,22 +62,22 @@ public NameEnvironmentAnswer readClassFile(String filename, char[][] packageName
}
}
public NameEnvironmentAnswer readJavaFile(String filename, char[][] packageName) {
+ InputStream stream = null;
try {
String fullName = FileSystem.assembleName(filename, packageName, '/');
ZipEntry entry = zipFile.getEntry(fullName);
- InputStreamReader reader = new InputStreamReader(zipFile.getInputStream(entry));
- int length;
- char[] contents = new char[length = (int) entry.getSize()];
- int len = 0;
- int readSize = 0;
- while ((readSize != -1) && (len != length)) {
- readSize = reader.read(contents, len, length - len);
- len += readSize;
- }
- reader.close();
+ stream = new BufferedInputStream(zipFile.getInputStream(entry));
+ char[] contents = Util.getInputStreamAsCharArray(stream, (int) entry.getSize());
return new NameEnvironmentAnswer(new CompilationUnit(contents, fullName));
} catch (Exception e) {
return null; // treat as if source file is missing
+ } finally {
+ if (stream != null) {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
}
}
public String toString() {
diff --git a/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/CompilationUnit.java b/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/CompilationUnit.java
index b23c86baa9..19c0914186 100644
--- a/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/CompilationUnit.java
+++ b/org.eclipse.jdt.core/batch/org/eclipse/jdt/internal/compiler/batch/CompilationUnit.java
@@ -7,6 +7,7 @@ package org.eclipse.jdt.internal.compiler.batch;
import java.io.*;
import org.eclipse.jdt.internal.compiler.env.*;
+import org.eclipse.jdt.internal.compiler.util.Util;
public class CompilationUnit implements ICompilationUnit {
public char[] contents;
@@ -31,36 +32,10 @@ public char[] getContents() {
return contents; // answer the cached source
// otherwise retrieve it
- BufferedReader reader = null;
try {
- File file = new File(new String(fileName));
- reader = new BufferedReader(new FileReader(file));
- int length;
- char[] contents = new char[length = (int) file.length()];
- int len = 0;
- int readSize = 0;
- while ((readSize != -1) && (len != length)) {
- // See PR 1FMS89U
- // We record first the read size. In this case len is the actual read size.
- len += readSize;
- readSize = reader.read(contents, len, length - len);
- }
- reader.close();
- // See PR 1FMS89U
- // Now we need to resize in case the default encoding used more than one byte for each
- // character
- if (len != length)
- System.arraycopy(contents, 0, (contents = new char[len]), 0, len);
- return contents;
- } catch (FileNotFoundException e) {
+ return Util.getFileCharContent(new File(new String(fileName)));
} catch (IOException e) {
- if (reader != null) {
- try {
- reader.close();
- } catch(IOException ioe) {
- }
- }
- };
+ }
return new char[0];
}
public char[] getFileName() {
diff --git a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java
index 92eca57ff9..6805658dff 100644
--- a/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java
+++ b/org.eclipse.jdt.core/codeassist/org/eclipse/jdt/internal/codeassist/impl/AssistParser.java
@@ -603,7 +603,7 @@ protected NameReference getUnspecifiedReferenceOptimized() {
/* completion inside subsequent identifier */
reference = this.createQualifiedAssistNameReference(subset, assistIdentifier(), positions);
};
- reference.bits &= ~NameReference.RestrictiveFlagMASK;
+ reference.bits &= ~AstNode.RestrictiveFlagMASK;
reference.bits |= LOCAL | FIELD;
assistNode = reference;
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/DocumentElementParser.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/DocumentElementParser.java
index 340864ca71..90483cd1cd 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/DocumentElementParser.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/DocumentElementParser.java
@@ -247,6 +247,7 @@ protected void consumeClassHeaderName() {
} else {
// Record that the block has a declaration for local types
typeDecl = new LocalTypeDeclaration();
+ markCurrentMethodWithLocalType();
blockReal();
}
@@ -482,6 +483,8 @@ protected void consumeEnterVariable() {
if ((baseType = identifierLengthStack[identifierLengthPtr + 1]) < 0) {
//it was a baseType
declaration.type = TypeReference.baseTypeReference(-baseType, dimension);
+ declaration.type.sourceStart = type.sourceStart;
+ declaration.type.sourceEnd = type.sourceEnd;
} else {
declaration.type = type.copyDims(dimension);
}
@@ -649,6 +652,7 @@ protected void consumeInterfaceHeaderName() {
} else {
// Record that the block has a declaration for local types
typeDecl = new LocalTypeDeclaration();
+ markCurrentMethodWithLocalType();
blockReal();
}
@@ -920,24 +924,6 @@ protected void consumeStaticOnly() {
nestedMethod[nestedType]++;
resetModifiers();
}
-protected void consumeToken(int type) {
- super.consumeToken(type);
-
- switch (type) {
- case TokenNamevoid :
- case TokenNameboolean :
- case TokenNamebyte :
- case TokenNamechar :
- case TokenNamedouble :
- case TokenNamefloat :
- case TokenNameint :
- case TokenNamelong :
- case TokenNameshort :
- // we need this position to know where the base type name ends.
- pushOnIntStack(scanner.currentPosition - 1);
- break;
- }
-}
/**
*
* INTERNAL USE-ONLY
@@ -999,12 +985,18 @@ This variable is a type reference and dim will be its dimensions*/
identifierStack[identifierPtr],
dim,
identifierPositionStack[identifierPtr--]);
+ ref.sourceEnd = endPosition;
}
} else {
if (length < 0) { //flag for precompiled type reference on base types
ref = TypeReference.baseTypeReference(-length, dim);
- ref.sourceEnd = intStack[intPtr--];
ref.sourceStart = intStack[intPtr--];
+ if (dim == 0) {
+ ref.sourceEnd = intStack[intPtr--];
+ } else {
+ intPtr--;
+ ref.sourceEnd = endPosition;
+ }
} else { //Qualified variable reference
char[][] tokens = new char[length][];
identifierPtr -= length;
@@ -1016,10 +1008,12 @@ This variable is a type reference and dim will be its dimensions*/
positions,
0,
length);
- if (dim == 0)
+ if (dim == 0) {
ref = new QualifiedTypeReference(tokens, positions);
- else
+ } else {
ref = new ArrayQualifiedTypeReference(tokens, dim, positions);
+ ref.sourceEnd = endPosition;
+ }
}
};
return ref;
@@ -1301,12 +1295,18 @@ protected TypeReference typeReference(
identifierStack[localIdentifierPtr],
dim,
identifierPositionStack[localIdentifierPtr--]);
+ ref.sourceEnd = endPosition;
}
} else {
if (length < 0) { //flag for precompiled type reference on base types
ref = TypeReference.baseTypeReference(-length, dim);
- ref.sourceEnd = intStack[localIntPtr--];
ref.sourceStart = intStack[localIntPtr--];
+ if (dim == 0) {
+ ref.sourceEnd = intStack[localIntPtr--];
+ } else {
+ localIntPtr--;
+ ref.sourceEnd = endPosition;
+ }
} else { //Qualified variable reference
char[][] tokens = new char[length][];
localIdentifierPtr -= length;
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java
index d867c09ae4..973b2e6015 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java
@@ -131,9 +131,10 @@ public CompilationResult compilationResult(){
*/
public void generateCode(ClassScope classScope, ClassFile classFile) {
int problemResetPC = 0;
+ classFile.codeStream.wideMode = false; // reset wideMode to false
if (ignoreFurtherInvestigation) {
- if (this.binding == null)
- return; // Handle methods with invalid signature or duplicates
+ // method is known to have errors, dump a problem method
+ if (this.binding == null) return; // handle methods with invalid signature or duplicates
int problemsLength;
IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
@@ -141,52 +142,76 @@ public void generateCode(ClassScope classScope, ClassFile classFile) {
classFile.addProblemMethod(this, binding, problemsCopy);
return;
}
+ // regular code generation
try {
problemResetPC = classFile.contentsOffset;
- classFile.generateMethodInfoHeader(binding);
- int methodAttributeOffset = classFile.contentsOffset;
- int attributeNumber = classFile.generateMethodInfoAttribute(binding);
- if ((!binding.isNative()) && (!binding.isAbstract())) {
- int codeAttributeOffset = classFile.contentsOffset;
- classFile.generateCodeAttributeHeader();
- CodeStream codeStream = classFile.codeStream;
- codeStream.reset(this, classFile);
- // initialize local positions
- scope.computeLocalVariablePositions(binding.isStatic() ? 0 : 1, codeStream);
-
- // arguments initialization for local variable debug attributes
- if (arguments != null) {
- for (int i = 0, max = arguments.length; i < max; i++) {
- LocalVariableBinding argBinding;
- codeStream.addVisibleLocalVariable(argBinding = arguments[i].binding);
- argBinding.recordInitializationStartPC(0);
- }
- }
- if (statements != null) {
- for (int i = 0, max = statements.length; i < max; i++)
- statements[i].generateCode(scope, codeStream);
- }
- if (needFreeReturn) {
- codeStream.return_();
+ this.generateCode(classFile);
+ } catch (AbortMethod e) {
+ // a fatal error was detected during code generation, need to restart code gen if possible
+ if (e.compilationResult == CodeStream.RESTART_IN_WIDE_MODE) {
+ // a branch target required a goto_w, restart code gen in wide mode.
+ try {
+ this.traverse(new ResetSateForCodeGenerationVisitor(), classScope);
+ classFile.contentsOffset = problemResetPC;
+ classFile.methodCount--;
+ classFile.codeStream.wideMode = true; // request wide mode
+ this.generateCode(classFile); // restart method generation
+ } catch(AbortMethod e2) {
+ int problemsLength;
+ IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
+ IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
+ System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
+ classFile.addProblemMethod(this, binding, problemsCopy, problemResetPC);
}
- // local variable attributes
- codeStream.exitUserScope(scope);
- codeStream.recordPositionsFrom(0, this);
- classFile.completeCodeAttribute(codeAttributeOffset);
- attributeNumber++;
+ } else {
+ // produce a problem method accounting for this fatal error
+ int problemsLength;
+ IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
+ IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
+ System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
+ classFile.addProblemMethod(this, binding, problemsCopy, problemResetPC);
}
- classFile.completeMethodInfo(methodAttributeOffset, attributeNumber);
+ }
+}
- // if a problem got reported during code gen, then trigger problem method creation
- if (ignoreFurtherInvestigation){
- throw new AbortMethod(scope.referenceCompilationUnit().compilationResult);
+private void generateCode(ClassFile classFile) {
+ classFile.generateMethodInfoHeader(binding);
+ int methodAttributeOffset = classFile.contentsOffset;
+ int attributeNumber = classFile.generateMethodInfoAttribute(binding);
+ if ((!binding.isNative()) && (!binding.isAbstract())) {
+ int codeAttributeOffset = classFile.contentsOffset;
+ classFile.generateCodeAttributeHeader();
+ CodeStream codeStream = classFile.codeStream;
+ codeStream.reset(this, classFile);
+ // initialize local positions
+ scope.computeLocalVariablePositions(binding.isStatic() ? 0 : 1, codeStream);
+
+ // arguments initialization for local variable debug attributes
+ if (arguments != null) {
+ for (int i = 0, max = arguments.length; i < max; i++) {
+ LocalVariableBinding argBinding;
+ codeStream.addVisibleLocalVariable(argBinding = arguments[i].binding);
+ argBinding.recordInitializationStartPC(0);
+ }
}
- } catch (AbortMethod e) {
- int problemsLength;
- IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
- IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
- System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
- classFile.addProblemMethod(this, binding, problemsCopy, problemResetPC);
+ if (statements != null) {
+ for (int i = 0, max = statements.length; i < max; i++)
+ statements[i].generateCode(scope, codeStream);
+ }
+ if (needFreeReturn) {
+ codeStream.return_();
+ }
+ // local variable attributes
+ codeStream.exitUserScope(scope);
+ codeStream.recordPositionsFrom(0, this);
+ classFile.completeCodeAttribute(codeAttributeOffset);
+ attributeNumber++;
+ }
+ classFile.completeMethodInfo(methodAttributeOffset, attributeNumber);
+
+ // if a problem got reported during code gen, then trigger problem method creation
+ if (ignoreFurtherInvestigation){
+ throw new AbortMethod(scope.referenceCompilationUnit().compilationResult);
}
}
public boolean isAbstract(){
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AstNode.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AstNode.java
index 8b1bb6550b..0a1af63330 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AstNode.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/AstNode.java
@@ -15,6 +15,68 @@ public abstract class AstNode implements BaseTypes, CompilerModifiers, TypeCons
//some global provision for the hierarchy
public final static Constant NotAConstant = Constant.NotAConstant;
+
+ // storage for internal flags (32 bits)
+ public int bits = IsReachableMASK; // reachable by default
+
+ // for operators only
+ // Reach . . . . . . . . . . . . . . . . . O O O O O O V VrR R R R
+ public static final int ReturnTypeIDMASK = 15; // 4 lower bits for operators
+ public static final int ValueForReturnMASK = 16; // for binary expressions
+ public static final int OnlyValueRequiredMASK = 32; // for binary expressions
+ public static final int OperatorSHIFT = 6;
+ public static final int OperatorMASK = 63 << OperatorSHIFT;
+
+ // for name references only
+ // Reach . . . . . . . . . . . . . . . . D D D D D D D D VrF R R R
+ public static final int RestrictiveFlagMASK = 7; // 3 lower bits for name references
+ public static final int FirstAssignmentToLocalMASK = 8; // for single name references
+ public static final int DepthSHIFT = 5;
+ public static final int DepthMASK = 0xFF << DepthSHIFT; // 8 bits for actual depth value (max. 255)
+
+ // for statements only
+ public static final int IsReachableMASK = 0x80000000; // highest bit
+
+ // for type declaration only
+ public static final int AddAssertionMASK = 1; // lowest bit
+
+ // for type, method and field declarations only
+ public static final int HasLocalTypeMASK = 2; // cannot conflict with AddAssertionMASK
+
+ /*
+ public final static int BitMask1= 0x1; // decimal 1
+ public final static int BitMask2= 0x2; // decimal 2
+ public final static int BitMask3= 0x4; // decimal 4
+ public final static int BitMask4= 0x8; // decimal 8
+ public final static int BitMask5= 0x10; // decimal 16
+ public final static int BitMask6= 0x20; // decimal 32
+ public final static int BitMask7= 0x40; // decimal 64
+ public final static int BitMask8= 0x80; // decimal 128
+ public final static int BitMask9= 0x100; // decimal 256
+ public final static int BitMask10= 0x200; // decimal 512
+ public final static int BitMask11= 0x400; // decimal 1024
+ public final static int BitMask12= 0x800; // decimal 2048
+ public final static int BitMask13= 0x1000; // decimal 4096
+ public final static int BitMask14= 0x2000; // decimal 8192
+ public final static int BitMask15= 0x4000; // decimal 16384
+ public final static int BitMask16= 0x8000; // decimal 32768
+ public final static int BitMask17= 0x10000; // decimal 65536
+ public final static int BitMask18= 0x20000; // decimal 131072
+ public final static int BitMask19= 0x40000; // decimal 262144
+ public final static int BitMask20= 0x80000; // decimal 524288
+ public final static int BitMask21= 0x100000; // decimal 1048576
+ public final static int BitMask22= 0x200000; // decimal 2097152
+ public final static int BitMask23= 0x400000; // decimal 4194304
+ public final static int BitMask24= 0x800000; // decimal 8388608
+ public final static int BitMask25= 0x1000000; // decimal 16777216
+ public final static int BitMask26= 0x2000000; // decimal 33554432
+ public final static int BitMask27= 0x4000000; // decimal 67108864
+ public final static int BitMask28= 0x8000000; // decimal 134217728
+ public final static int BitMask29= 0x10000000; // decimal 268435456
+ public final static int BitMask30= 0x20000000; // decimal 536870912
+ public final static int BitMask31= 0x40000000; // decimal 1073741824
+ public final static int BitMask32= 0x80000000; // decimal 2147483648
+ */
/**
* AstNode constructor comment.
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/BinaryExpression.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/BinaryExpression.java
index c33b663016..57aae22d9a 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/BinaryExpression.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/BinaryExpression.java
@@ -519,28 +519,7 @@ public void generateCode(BlockScope currentScope, CodeStream codeStream, boolean
public void generateOptimizedBoolean(BlockScope currentScope, CodeStream codeStream, Label trueLabel, Label falseLabel, boolean valueRequired) {
if ((constant != Constant.NotAConstant) && (constant.typeID() == T_boolean)) {
- int pc = codeStream.position;
- if (constant.booleanValue() == true) {
- // constant == true
- if (valueRequired) {
- if (falseLabel == null) {
- // implicit falling through the FALSE case
- if (trueLabel != null) {
- codeStream.goto_(trueLabel);
- }
- }
- }
- } else {
- if (valueRequired) {
- if (falseLabel != null) {
- // implicit falling through the TRUE case
- if (trueLabel == null) {
- codeStream.goto_(falseLabel);
- }
- }
- }
- }
- codeStream.recordPositionsFrom(pc, this);
+ super.generateOptimizedBoolean(currentScope, codeStream, trueLabel, falseLabel, valueRequired);
return;
}
switch((bits & OperatorMASK) >> OperatorSHIFT){
@@ -1275,7 +1254,6 @@ public boolean isCompactableOperation() {
return true;
}
public void optimizedBooleanConstant(int leftId, int operator, int rightId) {
- //watch for optimizedBooleanConstant
switch (operator) {
case AND :
@@ -1310,7 +1288,7 @@ public void optimizedBooleanConstant(int leftId, int operator, int rightId) {
return;
} else { //left is equivalent to false
if ((cst = right.conditionalConstant()) != NotAConstant) {
- optimizedBooleanConstant = Constant.fromValue(!cst.booleanValue()); // the conditional result is equivalent to the opposite of the right conditional value
+ optimizedBooleanConstant = cst;
}
return;
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Block.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Block.java
index 68af753317..7a29032b4a 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Block.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Block.java
@@ -11,119 +11,131 @@ import org.eclipse.jdt.internal.compiler.flow.*;
import org.eclipse.jdt.internal.compiler.lookup.*;
public class Block extends Statement {
+
public Statement[] statements;
- public int explicitDeclarations; // the number of explicit declaration , used to create scope
+ public int explicitDeclarations;
+ // the number of explicit declaration , used to create scope
public BlockScope scope;
public static final Block None = new Block(0);
-public Block(int explicitDeclarations) {
- this.explicitDeclarations = explicitDeclarations;
-}
-public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, FlowInfo flowInfo) {
-
- // iterate on statements
+
+ public Block(int explicitDeclarations) {
+ this.explicitDeclarations = explicitDeclarations;
+ }
+
+ public FlowInfo analyseCode(
+ BlockScope currentScope,
+ FlowContext flowContext,
+ FlowInfo flowInfo) {
- // empty block
- if (statements == null)
- return flowInfo;
- for (int i = 0, max = statements.length; i < max; i++) {
- Statement stat;
- if (!flowInfo.complainIfUnreachable((stat = statements[i]), scope)) {
- flowInfo = stat.analyseCode(scope, flowContext, flowInfo);
+ // empty block
+ if (statements == null)
+ return flowInfo;
+ for (int i = 0, max = statements.length; i < max; i++) {
+ Statement stat;
+ if (!flowInfo.complainIfUnreachable((stat = statements[i]), scope)) {
+ flowInfo = stat.analyseCode(scope, flowContext, flowInfo);
+ }
}
+ return flowInfo;
}
- return flowInfo;
-}
-public static final Block EmptyWith(int sourceStart, int sourceEnd) {
- //return an empty block which position is s and e
- Block bk = new Block(0);
- bk.sourceStart = sourceStart;
- bk.sourceEnd = sourceEnd;
- return bk;
-}
-/**
- * Code generation for a block
- * i.e. propagate to statements
- */
-public void generateCode(BlockScope currentScope, CodeStream codeStream) {
- if ((bits & IsReachableMASK) == 0) {
- return;
+ public static final Block EmptyWith(int sourceStart, int sourceEnd) {
+ //return an empty block which position is s and e
+ Block bk = new Block(0);
+ bk.sourceStart = sourceStart;
+ bk.sourceEnd = sourceEnd;
+ return bk;
}
- int pc = codeStream.position;
- if (statements != null) {
- for (int i = 0, max = statements.length; i < max; i++) {
- statements[i].generateCode(scope, codeStream);
+
+ /**
+ * Code generation for a block
+ */
+ public void generateCode(BlockScope currentScope, CodeStream codeStream) {
+ if ((bits & IsReachableMASK) == 0) {
+ return;
}
- } // for local variable debug attributes
- if (scope != currentScope){ // was really associated with its own scope
- codeStream.exitUserScope(scope);
+ int pc = codeStream.position;
+ if (statements != null) {
+ for (int i = 0, max = statements.length; i < max; i++) {
+ statements[i].generateCode(scope, codeStream);
+ }
+ } // for local variable debug attributes
+ if (scope != currentScope) { // was really associated with its own scope
+ codeStream.exitUserScope(scope);
+ }
+ codeStream.recordPositionsFrom(pc, this);
}
- codeStream.recordPositionsFrom(pc, this);
-}
-public boolean isEmptyBlock(){
- return statements == null;
-}
-public void resolve(BlockScope upperScope) {
- if (statements != null) {
- scope = explicitDeclarations == 0 ? upperScope : new BlockScope(upperScope, explicitDeclarations);
- int i = 0, length = statements.length;
- while (i < length)
- statements[i++].resolve(scope);
+
+ public boolean isEmptyBlock() {
+ return statements == null;
}
-}
-public void resolveUsing(BlockScope givenScope) {
- // this optimized resolve(...) is sent only on none empty blocks
- scope = givenScope;
- if (statements != null) {
- int i = 0, length = statements.length;
- while (i < length)
- statements[i++].resolve(scope);
+ public void resolve(BlockScope upperScope) {
+ if (statements != null) {
+ scope =
+ explicitDeclarations == 0
+ ? upperScope
+ : new BlockScope(upperScope, explicitDeclarations);
+ int i = 0, length = statements.length;
+ while (i < length)
+ statements[i++].resolve(scope);
+ }
+ }
+
+ public void resolveUsing(BlockScope givenScope) {
+ // this optimized resolve(...) is sent only on none empty blocks
+ scope = givenScope;
+ if (statements != null) {
+ int i = 0, length = statements.length;
+ while (i < length)
+ statements[i++].resolve(scope);
+ }
}
-}
-public String toString(int tab) {
- /* slow code */
- String s = tabString(tab);
- if (this.statements == null) {
+ public String toString(int tab) {
+ /* slow code */
+ String s = tabString(tab);
+ if (this.statements == null) {
+ s += "{\n"; //$NON-NLS-1$
+ s += tabString(tab);
+ s += "}"; //$NON-NLS-1$
+ return s;
+ }
+ // s = s + (explicitDeclarations != 0
+ // ? " { // ---scope needed for "+String.valueOf(explicitDeclarations) +" locals------------ \n"
+ // : "{// ---NO scope needed------ \n") ;
s += "{\n"; //$NON-NLS-1$
+ s += this.toStringStatements(tab);
s += tabString(tab);
s += "}"; //$NON-NLS-1$
return s;
}
- // s = s + (explicitDeclarations != 0
- // ? " { // ---scope needed for "+String.valueOf(explicitDeclarations) +" locals------------ \n"
- // : "{// ---NO scope needed------ \n") ;
+ public String toStringStatements(int tab) {
+ if (this.statements == null)
+ return ""; //$NON-NLS-1$
+ StringBuffer buffer = new StringBuffer();
+ for (int i = 0; i < statements.length; i++) {
+ buffer.append(statements[i].toString(tab + 1));
+ if (statements[i] instanceof Block) {
+ buffer.append("\n"); //$NON-NLS-1$
+ } else {
+ buffer.append(";\n"); //$NON-NLS-1$
+ }
+ };
+ return buffer.toString();
+ }
- s += "{\n"; //$NON-NLS-1$
- s += this.toStringStatements(tab);
- s += tabString(tab);
- s += "}"; //$NON-NLS-1$
- return s;
-}
-public String toStringStatements(int tab) {
- /* slow code */
- if (this.statements == null) return ""; //$NON-NLS-1$
- StringBuffer buffer = new StringBuffer();
- for (int i = 0; i < statements.length; i++) {
- buffer.append(statements[i].toString(tab + 1));
- if (statements[i] instanceof Block){
- buffer.append("\n"); //$NON-NLS-1$
- } else {
- buffer.append(";\n"); //$NON-NLS-1$
- }
- };
- return buffer.toString();
-}
-public void traverse(IAbstractSyntaxTreeVisitor visitor, BlockScope blockScope) {
- if (visitor.visit(this, blockScope)) {
- if (statements != null) {
- int statementLength = statements.length;
- for (int i = 0; i < statementLength; i++)
- statements[i].traverse(visitor, scope);
+ public void traverse(
+ IAbstractSyntaxTreeVisitor visitor,
+ BlockScope blockScope) {
+ if (visitor.visit(this, blockScope)) {
+ if (statements != null) {
+ int statementLength = statements.length;
+ for (int i = 0; i < statementLength; i++)
+ statements[i].traverse(visitor, scope);
+ }
}
+ visitor.endVisit(this, blockScope);
}
- visitor.endVisit(this, blockScope);
-}
-}
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Break.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Break.java
index 7bd0d7d809..02b2518715 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Break.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Break.java
@@ -48,6 +48,10 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
break;
}
}
+ // remember the initialization at this
+ // point for dealing with blank final variables.
+ traversedContext.recordReturnFrom(flowInfo.unconditionalInits());
+
if (traversedContext == targetContext) {
break;
} else {
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/CompoundAssignment.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/CompoundAssignment.java
index 02af3ac153..3ff0ef9329 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/CompoundAssignment.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/CompoundAssignment.java
@@ -73,20 +73,20 @@ public String operatorToString() {
}
public TypeBinding resolveType(BlockScope scope) {
constant = NotAConstant;
- TypeBinding lhsTb = lhs.resolveType(scope);
- TypeBinding expressionTb = expression.resolveType(scope);
- if (lhsTb == null || expressionTb == null)
+ TypeBinding lhsType = lhs.resolveType(scope);
+ TypeBinding expressionType = expression.resolveType(scope);
+ if (lhsType == null || expressionType == null)
return null;
- int lhsId = lhsTb.id;
- int expressionId = expressionTb.id;
- if (restrainUsageToNumericTypes() && !lhsTb.isNumericType()) {
- scope.problemReporter().operatorOnlyValidOnNumericType(this, lhsTb, expressionTb);
+ int lhsId = lhsType.id;
+ int expressionId = expressionType.id;
+ if (restrainUsageToNumericTypes() && !lhsType.isNumericType()) {
+ scope.problemReporter().operatorOnlyValidOnNumericType(this, lhsType, expressionType);
return null;
}
if (lhsId > 15 || expressionId > 15) {
if (lhsId != T_String) { // String += Object is valid wheraas Object -= String is not
- scope.problemReporter().invalidOperator(this, lhsTb, expressionTb);
+ scope.problemReporter().invalidOperator(this, lhsType, expressionType);
return null;
}
expressionId = T_Object; // use the Object has tag table
@@ -100,19 +100,24 @@ public TypeBinding resolveType(BlockScope scope) {
// the conversion is stored INTO the reference (info needed for the code gen)
int result = OperatorExpression.ResolveTypeTables[operator][ (lhsId << 4) + expressionId];
if (result == T_undefined) {
- scope.problemReporter().invalidOperator(this, lhsTb, expressionTb);
+ scope.problemReporter().invalidOperator(this, lhsType, expressionType);
return null;
}
- if (operator == PLUS && scope.isJavaLangObject(lhsTb)) {
- // Object o = "hello";
- // o += " world" // <--illegal
- scope.problemReporter().invalidOperator(this, lhsTb, expressionTb);
- return null;
+ if (operator == PLUS){
+ if(scope.isJavaLangObject(lhsType)) {
+ // <Object> += <String> is illegal
+ scope.problemReporter().invalidOperator(this, lhsType, expressionType);
+ return null;
+ } else if ((lhsType.isNumericType() || lhsId == T_boolean) && !expressionType.isNumericType()){
+ // <int | boolean> += <String> is illegal
+ scope.problemReporter().invalidOperator(this, lhsType, expressionType);
+ return null;
+ }
}
lhs.implicitConversion = result >>> 12;
expression.implicitConversion = (result >>> 4) & 0x000FF;
assignmentImplicitConversion = (lhsId << 4) + (result & 0x0000F);
- return lhsTb;
+ return lhsType;
}
public boolean restrainUsageToNumericTypes(){
return false ;}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ConstructorDeclaration.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ConstructorDeclaration.java
index 911fda0dc8..fc462275e7 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ConstructorDeclaration.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ConstructorDeclaration.java
@@ -116,6 +116,37 @@ public void generateCode(ClassScope classScope, ClassFile classFile) {
}
try {
problemResetPC = classFile.contentsOffset;
+ this.internalGenerateCode(classScope, classFile);
+ } catch (AbortMethod e) {
+ if (e.compilationResult == CodeStream.RESTART_IN_WIDE_MODE) {
+ // a branch target required a goto_w, restart code gen in wide mode.
+ try {
+ if (statements != null) {
+ for (int i = 0, max = statements.length; i < max; i++)
+ statements[i].resetStateForCodeGeneration();
+ }
+ classFile.contentsOffset = problemResetPC;
+ classFile.methodCount--;
+ classFile.codeStream.wideMode = true; // request wide mode
+ this.internalGenerateCode(classScope, classFile); // restart method generation
+ } catch(AbortMethod e2) {
+ int problemsLength;
+ IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
+ IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
+ System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
+ classFile.addProblemConstructor(this, binding, problemsCopy, problemResetPC);
+ }
+ } else {
+ int problemsLength;
+ IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
+ IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
+ System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
+ classFile.addProblemConstructor(this, binding, problemsCopy, problemResetPC);
+ }
+ }
+}
+
+private void internalGenerateCode(ClassScope classScope, ClassFile classFile) {
classFile.generateMethodInfoHeader(binding);
int methodAttributeOffset = classFile.contentsOffset;
int attributeNumber = classFile.generateMethodInfoAttribute(binding);
@@ -204,13 +235,6 @@ public void generateCode(ClassScope classScope, ClassFile classFile) {
if (ignoreFurtherInvestigation){
throw new AbortMethod(scope.referenceCompilationUnit().compilationResult);
}
- } catch (AbortMethod e) {
- int problemsLength;
- IProblem[] problems = scope.referenceCompilationUnit().compilationResult.getProblems();
- IProblem[] problemsCopy = new IProblem[problemsLength = problems.length];
- System.arraycopy(problems, 0, problemsCopy, 0, problemsLength);
- classFile.addProblemConstructor(this, binding, problemsCopy, problemResetPC);
- }
}
public boolean isConstructor() {
return true;
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Continue.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Continue.java
index 2d08037c54..933f3cedf7 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Continue.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Continue.java
@@ -52,6 +52,10 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
break;
}
}
+ // remember the initialization at this
+ // point for dealing with blank final variables.
+ traversedContext.recordReturnFrom(flowInfo.unconditionalInits());
+
if (traversedContext == targetContext) {
break;
} else {
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/DoStatement.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/DoStatement.java
index efac89ddcb..fd2acb7dbb 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/DoStatement.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/DoStatement.java
@@ -145,4 +145,9 @@ public void traverse(IAbstractSyntaxTreeVisitor visitor, BlockScope scope) {
}
visitor.endVisit(this, scope);
}
+
+public void resetStateForCodeGeneration() {
+ this.breakLabel.resetStateForCodeGeneration();
+ this.continueLabel.resetStateForCodeGeneration();
+}
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/IfStatement.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/IfStatement.java
index 3b66dcdfef..fc32733a17 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/IfStatement.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/IfStatement.java
@@ -82,6 +82,7 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
// merge THEN & ELSE initializations
FlowInfo mergedInfo;
if ((condition.constant != NotAConstant) && (condition.constant.booleanValue() == true)) {
+ // IF (TRUE)
if (thenExit) {
mergedInfo = elseFlowInfo.markAsFakeReachable(true);
mergedInitStateIndex = currentScope.methodScope().recordInitializationStates(mergedInfo);
@@ -91,6 +92,7 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
return thenFlowInfo;
}
} else {
+ // IF (FALSE)
if ((condition.constant != NotAConstant) && (condition.constant.booleanValue() == false)) {
if (elseFlowInfo.isDeadEnd()) {
mergedInfo = thenFlowInfo.markAsFakeReachable(true);
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/LabeledStatement.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/LabeledStatement.java
index 3fca23c095..7ec80bf807 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/LabeledStatement.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/LabeledStatement.java
@@ -86,4 +86,7 @@ public void traverse(IAbstractSyntaxTreeVisitor visitor, BlockScope blockScope)
}
visitor.endVisit(this, blockScope);
}
+public void resetStateForCodeGeneration() {
+ this.targetLabel.resetStateForCodeGeneration();
+}
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ReturnStatement.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ReturnStatement.java
index 041b3a07fe..df52657093 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ReturnStatement.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/ReturnStatement.java
@@ -66,6 +66,10 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
}
}
}
+ // remember the initialization at this
+ // point for dealing with blank final variables.
+ traversedContext.recordReturnFrom(flowInfo.unconditionalInits());
+
FlowContext parentContext;
if ((parentContext = traversedContext.parent) == null) { // top-context
break;
@@ -77,9 +81,6 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
if ((subroutines != null) && (subIndex != maxSub)) {
System.arraycopy(subroutines, 0, (subroutines = new AstNode[subIndex]), 0, subIndex);
}
- // the top returning context may want to remember the initialization at this
- // point for dealing with blank final fields.
- traversedContext.recordReturnFrom(flowInfo.unconditionalInits());
// no need to save a constant value
if((expression != null) && (expression.constant != NotAConstant)){
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/TryStatement.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/TryStatement.java
index 7531da270b..be02c40b31 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/TryStatement.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/TryStatement.java
@@ -58,14 +58,16 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
if (returnAddressVariable != null) {
returnAddressVariable.used = true;
}
- FlowContext insideSubContext;
+ InsideSubRoutineFlowContext insideSubContext;
FinallyFlowContext finallyContext;
UnconditionalFlowInfo subInfo;
if (subRoutineStartLabel == null) {
- insideSubContext = flowContext;
+ // no finally block
+ insideSubContext = null;
finallyContext = null;
subInfo = null;
} else {
+ // analyse finally block first
insideSubContext = new InsideSubRoutineFlowContext(flowContext, this);
subInfo = finallyBlock.analyseCode(
currentScope,
@@ -76,10 +78,15 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
subRoutineCannotReturn = false;
}
}
-
// process the try block in a context handling the local exceptions.
ExceptionHandlingFlowContext handlingContext =
- new ExceptionHandlingFlowContext(insideSubContext, tryBlock, caughtExceptionTypes, scope, flowInfo.unconditionalInits());
+ new ExceptionHandlingFlowContext(
+ insideSubContext == null ? flowContext: insideSubContext,
+ tryBlock,
+ caughtExceptionTypes,
+ scope,
+ flowInfo.unconditionalInits());
+
FlowInfo tryInfo;
if (tryBlock.statements == null) {
tryInfo = flowInfo;
@@ -100,7 +107,8 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
// keep track of the inits that could potentially have led to this exception handler (for final assignments diagnosis)
///*
FlowInfo catchInfo = flowInfo.copy().unconditionalInits()
- .addPotentialInitializationsFrom(handlingContext.initsOnException(caughtExceptionTypes[i]).unconditionalInits())
+ .addPotentialInitializationsFrom(
+ handlingContext.initsOnException(caughtExceptionTypes[i]).unconditionalInits())
.addPotentialInitializationsFrom(tryInfo.unconditionalInits());
//*/
// SMART ANALYSIS (see 1FBPLCY)
@@ -118,7 +126,10 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
if (tryBlock.statements == null) {
catchInfo.markAsFakeReachable(true);
}
- catchInfo = catchBlocks[i].analyseCode(currentScope, insideSubContext, catchInfo);
+ catchInfo = catchBlocks[i].analyseCode(
+ currentScope,
+ insideSubContext == null ? flowContext: insideSubContext,
+ catchInfo);
catchExits[i] = ((catchInfo == FlowInfo.DeadEnd) || catchInfo.isFakeReachable());
tryInfo = tryInfo.mergedWith(catchInfo.unconditionalInits());
}
@@ -129,6 +140,8 @@ public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, Fl
}
// we also need to check potential multiple assignments of final variables inside the finally block
+ // need to include potential inits from returns inside the try/catch parts - 1GK2AOF
+ tryInfo.addPotentialInitializationsFrom(insideSubContext.initsOnReturn);
finallyContext.complainOnRedundantFinalAssignments(tryInfo, currentScope);
if (subInfo == FlowInfo.DeadEnd) {
mergedInitStateIndex = currentScope.methodScope().recordInitializationStates(subInfo);
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/UnaryExpression.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/UnaryExpression.java
index 3093dd5036..6d0f33668e 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/UnaryExpression.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/UnaryExpression.java
@@ -10,246 +10,270 @@ import org.eclipse.jdt.internal.compiler.codegen.*;
import org.eclipse.jdt.internal.compiler.flow.*;
import org.eclipse.jdt.internal.compiler.lookup.*;
-
public class UnaryExpression extends OperatorExpression {
+
public Expression expression;
public Constant optimizedBooleanConstant;
-public UnaryExpression(Expression expression, int operator) {
- this.expression = expression;
- this.bits |= operator << OperatorSHIFT; // encode operator
-}
-public FlowInfo analyseCode(BlockScope currentScope, FlowContext flowContext, FlowInfo flowInfo) {
- if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
- return expression.analyseCode(currentScope, flowContext, flowInfo).asNegatedCondition();
- } else {
- return expression.analyseCode(currentScope, flowContext, flowInfo);
+ public UnaryExpression(Expression expression, int operator) {
+ this.expression = expression;
+ this.bits |= operator << OperatorSHIFT; // encode operator
}
-}
-public Constant conditionalConstant(){
- return optimizedBooleanConstant == null ?
- constant :
- optimizedBooleanConstant ;}
-/**
- * Code generation for an unary operation
- *
- * @param currentScope org.eclipse.jdt.internal.compiler.lookup.BlockScope
- * @param codeStream org.eclipse.jdt.internal.compiler.codegen.CodeStream
- * @param valueRequired boolean
- */
-public void generateCode(BlockScope currentScope, CodeStream codeStream, boolean valueRequired) {
- int pc = codeStream.position;
- Label falseLabel, endifLabel;
- if (constant != Constant.NotAConstant) {
- // inlined value
- if (valueRequired){
- codeStream.generateConstant(constant, implicitConversion);
+ public FlowInfo analyseCode(
+ BlockScope currentScope,
+ FlowContext flowContext,
+ FlowInfo flowInfo) {
+ if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
+ return expression
+ .analyseCode(currentScope, flowContext, flowInfo)
+ .asNegatedCondition();
+ } else {
+ return expression.analyseCode(currentScope, flowContext, flowInfo);
}
- codeStream.recordPositionsFrom(pc, this);
- return;
}
- switch ((bits & OperatorMASK) >> OperatorSHIFT) {
- case NOT :
- switch (expression.implicitConversion >> 4 )/* runtime type */ {
- case T_boolean :
- // ! <boolean>
- // Generate code for the condition
- expression.generateOptimizedBoolean(currentScope, codeStream, null, (falseLabel = new Label(codeStream)), valueRequired);
- if (valueRequired) {
- codeStream.iconst_0();
- codeStream.goto_(endifLabel = new Label(codeStream));
- codeStream.decrStackSize(1);
- falseLabel.place();
- if (valueRequired)
- codeStream.iconst_1();
- endifLabel.place();
- }
- break;
+
+ public Constant conditionalConstant() {
+ return optimizedBooleanConstant == null ? constant : optimizedBooleanConstant;
+ }
+
+ /**
+ * Code generation for an unary operation
+ *
+ * @param currentScope org.eclipse.jdt.internal.compiler.lookup.BlockScope
+ * @param codeStream org.eclipse.jdt.internal.compiler.codegen.CodeStream
+ * @param valueRequired boolean
+ */
+ public void generateCode(
+ BlockScope currentScope,
+ CodeStream codeStream,
+ boolean valueRequired) {
+ int pc = codeStream.position;
+ Label falseLabel, endifLabel;
+ if (constant != Constant.NotAConstant) {
+ // inlined value
+ if (valueRequired) {
+ codeStream.generateConstant(constant, implicitConversion);
}
- break;
- case TWIDDLE :
- switch (expression.implicitConversion >> 4 /* runtime */) {
- case T_int :
- // ~int
- expression.generateCode(currentScope, codeStream, valueRequired);
+ codeStream.recordPositionsFrom(pc, this);
+ return;
+ }
+ switch ((bits & OperatorMASK) >> OperatorSHIFT) {
+ case NOT :
+ switch (expression.implicitConversion >> 4) /* runtime type */ {
+ case T_boolean :
+ // ! <boolean>
+ // Generate code for the condition
+ expression.generateOptimizedBoolean(
+ currentScope,
+ codeStream,
+ null,
+ (falseLabel = new Label(codeStream)),
+ valueRequired);
+ if (valueRequired) {
+ codeStream.iconst_0();
+ codeStream.goto_(endifLabel = new Label(codeStream));
+ codeStream.decrStackSize(1);
+ falseLabel.place();
+ if (valueRequired)
+ codeStream.iconst_1();
+ endifLabel.place();
+ }
+ break;
+ }
+ break;
+ case TWIDDLE :
+ switch (expression.implicitConversion >> 4 /* runtime */
+ ) {
+ case T_int :
+ // ~int
+ expression.generateCode(currentScope, codeStream, valueRequired);
+ if (valueRequired) {
+ codeStream.iconst_m1();
+ codeStream.ixor();
+ }
+ break;
+ case T_long :
+ expression.generateCode(currentScope, codeStream, valueRequired);
+ if (valueRequired) {
+ codeStream.ldc2_w(-1L);
+ codeStream.lxor();
+ }
+ }
+ break;
+ case MINUS :
+ // - <num>
+ if (constant != NotAConstant) {
if (valueRequired) {
- codeStream.iconst_m1();
- codeStream.ixor();
+ switch (expression.implicitConversion >> 4 /* runtime */
+ ) {
+ case T_int :
+ codeStream.generateInlinedValue(constant.intValue() * -1);
+ break;
+ case T_float :
+ codeStream.generateInlinedValue(constant.floatValue() * -1.0f);
+ break;
+ case T_long :
+ codeStream.generateInlinedValue(constant.longValue() * -1L);
+ break;
+ case T_double :
+ codeStream.generateInlinedValue(constant.doubleValue() * -1.0);
+ }
}
- break;
- case T_long :
+ } else {
expression.generateCode(currentScope, codeStream, valueRequired);
if (valueRequired) {
- codeStream.ldc2_w(-1L);
- codeStream.lxor();
- }
- }
- break;
- case MINUS :
- // - <num>
- if (constant != NotAConstant) {
- if (valueRequired) {
- switch (expression.implicitConversion >> 4 /* runtime */) {
- case T_int :
- codeStream.generateInlinedValue(constant.intValue() * -1);
- break;
- case T_float :
- codeStream.generateInlinedValue(constant.floatValue() * -1.0f);
- break;
- case T_long :
- codeStream.generateInlinedValue(constant.longValue() * -1L);
- break;
- case T_double :
- codeStream.generateInlinedValue(constant.doubleValue() * -1.0);
+ switch (expression.implicitConversion >> 4 /* runtime type */
+ ) {
+ case T_int :
+ codeStream.ineg();
+ break;
+ case T_float :
+ codeStream.fneg();
+ break;
+ case T_long :
+ codeStream.lneg();
+ break;
+ case T_double :
+ codeStream.dneg();
+ }
}
}
- } else {
+ break;
+ case PLUS :
expression.generateCode(currentScope, codeStream, valueRequired);
- if (valueRequired) {
- switch (expression.implicitConversion >> 4 /* runtime type */) {
- case T_int :
- codeStream.ineg();
- break;
- case T_float :
- codeStream.fneg();
- break;
- case T_long :
- codeStream.lneg();
- break;
- case T_double :
- codeStream.dneg();
- }
- }
- }
- break;
- case PLUS :
- expression.generateCode(currentScope, codeStream, valueRequired);
- }
- if (valueRequired) {
- codeStream.generateImplicitConversion(implicitConversion);
+ }
+ if (valueRequired) {
+ codeStream.generateImplicitConversion(implicitConversion);
+ }
+ codeStream.recordPositionsFrom(pc, this);
}
- codeStream.recordPositionsFrom(pc, this);
-}
-/**
- * Boolean operator code generation
- * Optimized operations are: &&, ||, <, <=, >, >=, &, |, ^
- */
-public void generateOptimizedBoolean(BlockScope currentScope, CodeStream codeStream, Label trueLabel, Label falseLabel, boolean valueRequired) {
- if ((constant != Constant.NotAConstant) && (constant.typeID() == T_boolean)) {
- int pc = codeStream.position;
- if (constant.booleanValue() == true) {
- // constant == true
- if (valueRequired) {
- if (falseLabel == null) {
- // implicit falling through the FALSE case
- if (trueLabel != null) {
- codeStream.goto_(trueLabel);
- }
- }
- }
+ /**
+ * Boolean operator code generation
+ * Optimized operations are: &&, ||, <, <=, >, >=, &, |, ^
+ */
+ public void generateOptimizedBoolean(
+ BlockScope currentScope,
+ CodeStream codeStream,
+ Label trueLabel,
+ Label falseLabel,
+ boolean valueRequired) {
+
+ if ((constant != Constant.NotAConstant) && (constant.typeID() == T_boolean)) {
+ super.generateOptimizedBoolean(
+ currentScope,
+ codeStream,
+ trueLabel,
+ falseLabel,
+ valueRequired);
+ return;
+ }
+ if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
+ expression.generateOptimizedBoolean(
+ currentScope,
+ codeStream,
+ falseLabel,
+ trueLabel,
+ valueRequired);
} else {
- if (valueRequired) {
- if (falseLabel != null) {
- // implicit falling through the TRUE case
- if (trueLabel == null) {
- codeStream.goto_(falseLabel);
- }
- }
- }
+ super.generateOptimizedBoolean(
+ currentScope,
+ codeStream,
+ trueLabel,
+ falseLabel,
+ valueRequired);
}
- codeStream.recordPositionsFrom(pc, this);
- return;
- }
- if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
- expression.generateOptimizedBoolean(currentScope, codeStream, falseLabel, trueLabel, valueRequired);
- } else {
- super.generateOptimizedBoolean(currentScope, codeStream, trueLabel, falseLabel, valueRequired);
- }
-}
-public TypeBinding resolveType(BlockScope scope) {
- TypeBinding expressionTb = expression.resolveType(scope);
- if (expressionTb == null){
- constant = NotAConstant;
- return null;
- }
- int expressionId = expressionTb.id;
- if (expressionId > 15) {
- constant = NotAConstant;
- scope.problemReporter().invalidOperator(this, expressionTb);
- return null;
}
- int tableId;
- switch ((bits & OperatorMASK) >> OperatorSHIFT) {
- case NOT :
- tableId = AND_AND;
- break;
- case TWIDDLE :
- tableId = LEFT_SHIFT;
- break;
- default :
- tableId = MINUS;
- } //+ and - cases
-
- // the code is an int
- // (cast) left Op (cast) rigth --> result
- // 0000 0000 0000 0000 0000
- // <<16 <<12 <<8 <<4 <<0
- int result = ResolveTypeTables[tableId][(expressionId << 4) + expressionId];
- expression.implicitConversion = result >>> 12;
- TypeBinding type;
- switch (result & 0x0000F) { // only switch on possible result type.....
- case T_boolean :
- type = BooleanBinding;
- break;
- case T_byte :
- type = ByteBinding;
- break;
- case T_char :
- type = CharBinding;
- break;
- case T_double :
- type = DoubleBinding;
- break;
- case T_float :
- type = FloatBinding;
- break;
- case T_int :
- type = IntBinding;
- break;
- case T_long :
- type = LongBinding;
- break;
- default : //error........
- constant = Constant.NotAConstant;
- if (expressionId != T_undefined)
- scope.problemReporter().invalidOperator(this, expressionTb);
+ public TypeBinding resolveType(BlockScope scope) {
+ TypeBinding expressionTb = expression.resolveType(scope);
+ if (expressionTb == null) {
+ constant = NotAConstant;
return null;
- }
+ }
+ int expressionId = expressionTb.id;
+ if (expressionId > 15) {
+ constant = NotAConstant;
+ scope.problemReporter().invalidOperator(this, expressionTb);
+ return null;
+ }
- // compute the constant when valid
- if (expression.constant != Constant.NotAConstant) {
- constant = Constant.computeConstantOperation(expression.constant, expressionId, (bits & OperatorMASK) >> OperatorSHIFT);
- } else {
- constant = Constant.NotAConstant;
- if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
- Constant cst = expression.conditionalConstant();
- if (cst.typeID() == T_boolean)
- optimizedBooleanConstant = Constant.fromValue(!cst.booleanValue());
+ int tableId;
+ switch ((bits & OperatorMASK) >> OperatorSHIFT) {
+ case NOT :
+ tableId = AND_AND;
+ break;
+ case TWIDDLE :
+ tableId = LEFT_SHIFT;
+ break;
+ default :
+ tableId = MINUS;
+ } //+ and - cases
+
+ // the code is an int
+ // (cast) left Op (cast) rigth --> result
+ // 0000 0000 0000 0000 0000
+ // <<16 <<12 <<8 <<4 <<0
+ int result = ResolveTypeTables[tableId][(expressionId << 4) + expressionId];
+ expression.implicitConversion = result >>> 12;
+ TypeBinding type;
+ switch (result & 0x0000F) { // only switch on possible result type.....
+ case T_boolean :
+ type = BooleanBinding;
+ break;
+ case T_byte :
+ type = ByteBinding;
+ break;
+ case T_char :
+ type = CharBinding;
+ break;
+ case T_double :
+ type = DoubleBinding;
+ break;
+ case T_float :
+ type = FloatBinding;
+ break;
+ case T_int :
+ type = IntBinding;
+ break;
+ case T_long :
+ type = LongBinding;
+ break;
+ default : //error........
+ constant = Constant.NotAConstant;
+ if (expressionId != T_undefined)
+ scope.problemReporter().invalidOperator(this, expressionTb);
+ return null;
+ }
+ // compute the constant when valid
+ if (expression.constant != Constant.NotAConstant) {
+ constant =
+ Constant.computeConstantOperation(
+ expression.constant,
+ expressionId,
+ (bits & OperatorMASK) >> OperatorSHIFT);
+ } else {
+ constant = Constant.NotAConstant;
+ if (((bits & OperatorMASK) >> OperatorSHIFT) == NOT) {
+ Constant cst = expression.conditionalConstant();
+ if (cst.typeID() == T_boolean)
+ optimizedBooleanConstant = Constant.fromValue(!cst.booleanValue());
+ }
}
+ return type;
}
- return type;
-}
-public String toStringExpressionNoParenthesis(){
- /* slow code*/
- return operatorToString() + " " + expression.toStringExpression() ; } //$NON-NLS-1$
-public void traverse(IAbstractSyntaxTreeVisitor visitor, BlockScope blockScope) {
- if (visitor.visit(this, blockScope)) {
- expression.traverse(visitor, blockScope);
+ public String toStringExpressionNoParenthesis() {
+ return operatorToString() + " " + expression.toStringExpression(); //$NON-NLS-1$
+ }
+
+ public void traverse(
+ IAbstractSyntaxTreeVisitor visitor,
+ BlockScope blockScope) {
+ if (visitor.visit(this, blockScope)) {
+ expression.traverse(visitor, blockScope);
+ }
+ visitor.endVisit(this, blockScope);
}
- visitor.endVisit(this, blockScope);
-}
-}
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/ExceptionHandlingFlowContext.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/ExceptionHandlingFlowContext.java
index 5445b6e710..058450a7b2 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/ExceptionHandlingFlowContext.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/ExceptionHandlingFlowContext.java
@@ -16,121 +16,113 @@ import org.eclipse.jdt.internal.compiler.codegen.*;
*/
public class ExceptionHandlingFlowContext extends FlowContext {
ReferenceBinding[] handledExceptions;
-
public final static int BitCacheSize = 32; // 32 bits per int
int[] isReached;
int[] isNeeded;
UnconditionalFlowInfo[] initsOnExceptions;
ObjectCache indexes = new ObjectCache();
boolean isMethodContext;
-public ExceptionHandlingFlowContext(
- FlowContext parent,
- AstNode associatedNode,
- ReferenceBinding[] handledExceptions,
- BlockScope scope,
- UnconditionalFlowInfo flowInfo) {
- super(parent, associatedNode);
- isMethodContext = scope == scope.methodScope();
-/*
- // for a method, append the unchecked exceptions to the handled exceptions collection
+ public ExceptionHandlingFlowContext(
+ FlowContext parent,
+ AstNode associatedNode,
+ ReferenceBinding[] handledExceptions,
+ BlockScope scope,
+ UnconditionalFlowInfo flowInfo) {
- if (scope.methodScope() == scope) {
- int length;
- System.arraycopy(
- handledExceptions,
- 0,
- (handledExceptions =
- new ReferenceBinding[(length = handledExceptions.length) + 2]),
- 0,
- length);
- handledExceptions[length] = scope.getJavaLangRuntimeException();
- handledExceptions[length + 1] = scope.getJavaLangError();
- }
-*/
- this.handledExceptions = handledExceptions;
- int count = handledExceptions.length, cacheSize = (count / BitCacheSize) + 1;
- isReached = new int[cacheSize]; // none is reached by default
- isNeeded = new int[cacheSize]; // none is needed by default
- initsOnExceptions = new UnconditionalFlowInfo[count];
- for (int i = 0; i < count; i++) {
- indexes.put(handledExceptions[i], i); // key type -> value index
- boolean isUnchecked =
- (scope.compareUncheckedException(handledExceptions[i]) != NotRelated);
- int cacheIndex = i / BitCacheSize, bitMask = 1 << (i % BitCacheSize);
- if (isUnchecked) {
- isReached[cacheIndex] |= bitMask;
- initsOnExceptions[i] = flowInfo.copy().unconditionalInits();
- } else {
- initsOnExceptions[i] = FlowInfo.DeadEnd;
+ super(parent, associatedNode);
+ isMethodContext = scope == scope.methodScope();
+ this.handledExceptions = handledExceptions;
+ int count = handledExceptions.length, cacheSize = (count / BitCacheSize) + 1;
+ this.isReached = new int[cacheSize]; // none is reached by default
+ this.isNeeded = new int[cacheSize]; // none is needed by default
+ this.initsOnExceptions = new UnconditionalFlowInfo[count];
+ for (int i = 0; i < count; i++) {
+ this.indexes.put(handledExceptions[i], i); // key type -> value index
+ boolean isUnchecked =
+ (scope.compareUncheckedException(handledExceptions[i]) != NotRelated);
+ int cacheIndex = i / BitCacheSize, bitMask = 1 << (i % BitCacheSize);
+ if (isUnchecked) {
+ isReached[cacheIndex] |= bitMask;
+ this.initsOnExceptions[i] = flowInfo.copy().unconditionalInits();
+ } else {
+ this.initsOnExceptions[i] = FlowInfo.DeadEnd;
+ }
}
+ System.arraycopy(this.isReached, 0, this.isNeeded, 0, cacheSize);
}
- System.arraycopy(isReached, 0, isNeeded, 0, cacheSize);
-}
-public void complainIfUnusedExceptionHandlers(AstNode[] exceptionHandlers, BlockScope scope, TryStatement tryStatement) {
-
- // report errors for unreachable exception handlers
- for (int i = 0, count = handledExceptions.length; i < count; i++) {
- int index = indexes.get(handledExceptions[i]);
- int cacheIndex = index / BitCacheSize;
- int bitMask = 1 << (index % BitCacheSize);
- if ((isReached[cacheIndex] & bitMask) == 0) {
- scope.problemReporter().unreachableExceptionHandler(
- handledExceptions[index],
- exceptionHandlers[index]);
- } else {
- if ((isNeeded[cacheIndex] & bitMask) == 0) {
- scope.problemReporter().maskedExceptionHandler(
- handledExceptions[index],
- exceptionHandlers[index]);
+ public void complainIfUnusedExceptionHandlers(
+ AstNode[] exceptionHandlers,
+ BlockScope scope,
+ TryStatement tryStatement) {
+ // report errors for unreachable exception handlers
+ for (int i = 0, count = handledExceptions.length; i < count; i++) {
+ int index = indexes.get(handledExceptions[i]);
+ int cacheIndex = index / BitCacheSize;
+ int bitMask = 1 << (index % BitCacheSize);
+ if ((isReached[cacheIndex] & bitMask) == 0) {
+ scope.problemReporter().unreachableExceptionHandler(
+ handledExceptions[index],
+ exceptionHandlers[index]);
+ } else {
+ if ((isNeeded[cacheIndex] & bitMask) == 0) {
+ scope.problemReporter().maskedExceptionHandler(
+ handledExceptions[index],
+ exceptionHandlers[index]);
+ }
}
}
+ // will optimized out unnecessary catch block during code gen
+ tryStatement.preserveExceptionHandler = isNeeded;
}
- // will optimized out unnecessary catch block during code gen
- tryStatement.preserveExceptionHandler = isNeeded;
-}
-public String individualToString() {
- StringBuffer buffer = new StringBuffer("Exception flow context"); //$NON-NLS-1$
- int length = handledExceptions.length;
- for (int i = 0; i < length; i++) {
- int cacheIndex = i / BitCacheSize;
- int bitMask = 1 << (i % BitCacheSize);
- buffer.append('[').append(handledExceptions[i].readableName());
- if ((isReached[cacheIndex] & bitMask) != 0) {
- if ((isNeeded[cacheIndex] & bitMask) == 0) {
- buffer.append("-masked"); //$NON-NLS-1$
+
+ public String individualToString() {
+ StringBuffer buffer = new StringBuffer("Exception flow context"); //$NON-NLS-1$
+ int length = handledExceptions.length;
+ for (int i = 0; i < length; i++) {
+ int cacheIndex = i / BitCacheSize;
+ int bitMask = 1 << (i % BitCacheSize);
+ buffer.append('[').append(handledExceptions[i].readableName());
+ if ((isReached[cacheIndex] & bitMask) != 0) {
+ if ((isNeeded[cacheIndex] & bitMask) == 0) {
+ buffer.append("-masked"); //$NON-NLS-1$
+ } else {
+ buffer.append("-reached"); //$NON-NLS-1$
+ }
} else {
- buffer.append("-reached"); //$NON-NLS-1$
+ buffer.append("-not reached"); //$NON-NLS-1$
}
- } else {
- buffer.append("-not reached"); //$NON-NLS-1$
+ buffer.append('-').append(initsOnExceptions[i].toString()).append(']');
}
- buffer.append('-').append(initsOnExceptions[i].toString()).append(']');
+ return buffer.toString();
}
- return buffer.toString();
-}
-public UnconditionalFlowInfo initsOnException(ReferenceBinding exceptionType) {
- int index;
- if ((index = indexes.get(exceptionType)) < 0) {
- return FlowInfo.DeadEnd;
+ public UnconditionalFlowInfo initsOnException(ReferenceBinding exceptionType) {
+ int index;
+ if ((index = indexes.get(exceptionType)) < 0) {
+ return FlowInfo.DeadEnd;
+ }
+ return initsOnExceptions[index];
}
- return initsOnExceptions[index];
-}
-public void recordHandlingException(ReferenceBinding exceptionType, UnconditionalFlowInfo flowInfo, TypeBinding raisedException, AstNode invocationSite, boolean wasAlreadyDefinitelyCaught) {
-
- int index = indexes.get(exceptionType);
- // if already flagged as being reached (unchecked exception handler)
- int cacheIndex = index / BitCacheSize;
- int bitMask = 1 << (index % BitCacheSize);
- if (!wasAlreadyDefinitelyCaught) {
- this.isNeeded[cacheIndex] |= bitMask;
+
+ public void recordHandlingException(
+ ReferenceBinding exceptionType,
+ UnconditionalFlowInfo flowInfo,
+ TypeBinding raisedException,
+ AstNode invocationSite,
+ boolean wasAlreadyDefinitelyCaught) {
+ int index = indexes.get(exceptionType);
+ // if already flagged as being reached (unchecked exception handler)
+ int cacheIndex = index / BitCacheSize;
+ int bitMask = 1 << (index % BitCacheSize);
+ if (!wasAlreadyDefinitelyCaught) {
+ this.isNeeded[cacheIndex] |= bitMask;
+ }
+ this.isReached[cacheIndex] |= bitMask;
+ initsOnExceptions[index] =
+ initsOnExceptions[index] == FlowInfo.DeadEnd
+ ? flowInfo.copy().unconditionalInits()
+ : initsOnExceptions[index].mergedWith(flowInfo);
}
- this.isReached[cacheIndex] |= bitMask;
- initsOnExceptions[index] =
- initsOnExceptions[index] == FlowInfo.DeadEnd
- ? flowInfo.copy().unconditionalInits()
- : initsOnExceptions[index].mergedWith(flowInfo);
-}
-}
+ } \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/FlowContext.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/FlowContext.java
index 632bc3e279..fcfad1a880 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/FlowContext.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/FlowContext.java
@@ -4,8 +4,6 @@ package org.eclipse.jdt.internal.compiler.flow;
* (c) Copyright IBM Corp. 2000, 2001.
* All Rights Reserved.
*/
-import java.util.*;
-
import org.eclipse.jdt.internal.compiler.*;
import org.eclipse.jdt.internal.compiler.ast.*;
import org.eclipse.jdt.internal.compiler.codegen.*;
@@ -13,6 +11,8 @@ import org.eclipse.jdt.internal.compiler.lookup.*;
import org.eclipse.jdt.internal.compiler.problem.*;
import org.eclipse.jdt.internal.compiler.util.*;
+import java.util.*;
+
/**
* Reflects the context of code analysis, keeping track of enclosing
* try statements, exception handlers, etc...
@@ -21,379 +21,393 @@ public class FlowContext implements TypeConstants {
public AstNode associatedNode;
public FlowContext parent;
- public final static FlowContext NotContinuableContext = new FlowContext(null,null);
-public FlowContext(FlowContext parent, AstNode associatedNode) {
- this.parent = parent;
- this.associatedNode = associatedNode;
-}
-public Label breakLabel() {
- return null;
-}
-public void checkExceptionHandlers(TypeBinding[] raisedExceptions, AstNode location, FlowInfo flowInfo, BlockScope scope) {
-
- // check that all the argument exception types are handled
-
- // JDK Compatible implementation - when an exception type is thrown,
- // all related catch blocks are marked as reachable... instead of those only
- // until the point where it is safely handled (Smarter - see comment at the end)
-
- int remainingCount; // counting the number of remaining unhandled exceptions
- int raisedCount; // total number of exceptions raised
- if ((raisedExceptions == null) || ((raisedCount = raisedExceptions.length) == 0))
- return;
- remainingCount = raisedCount;
-
- // duplicate the array of raised exceptions since it will be updated
- // (null replaces any handled exception)
- System.arraycopy(raisedExceptions, 0, (raisedExceptions = new TypeBinding[raisedCount]), 0, raisedCount);
- FlowContext traversedContext = this;
- while (traversedContext != null) {
- AstNode sub;
- if (((sub = traversedContext.subRoutine()) != null) && sub.cannotReturn()) {
- // traversing a non-returning subroutine means that all unhandled
- // exceptions will actually never get sent...
+ public final static FlowContext NotContinuableContext =
+ new FlowContext(null, null);
+
+ public FlowContext(FlowContext parent, AstNode associatedNode) {
+ this.parent = parent;
+ this.associatedNode = associatedNode;
+ }
+
+ public Label breakLabel() {
+ return null;
+ }
+
+ public void checkExceptionHandlers(
+ TypeBinding[] raisedExceptions,
+ AstNode location,
+ FlowInfo flowInfo,
+ BlockScope scope) {
+
+ // check that all the argument exception types are handled
+ // JDK Compatible implementation - when an exception type is thrown,
+ // all related catch blocks are marked as reachable... instead of those only
+ // until the point where it is safely handled (Smarter - see comment at the end)
+ int remainingCount; // counting the number of remaining unhandled exceptions
+ int raisedCount; // total number of exceptions raised
+ if ((raisedExceptions == null)
+ || ((raisedCount = raisedExceptions.length) == 0))
return;
- }
-
- // filter exceptions that are locally caught from the most enclosing
- // try statement to the outer ones.
- if (traversedContext instanceof ExceptionHandlingFlowContext) {
- ExceptionHandlingFlowContext exceptionContext = (ExceptionHandlingFlowContext) traversedContext;
- ReferenceBinding[] caughtExceptions;
- if ((caughtExceptions = exceptionContext.handledExceptions) != NoExceptions) {
- int caughtCount = caughtExceptions.length;
- boolean[] locallyCaught = new boolean[raisedCount]; // at most
-
- for (int caughtIndex = 0; caughtIndex < caughtCount; caughtIndex++) {
- ReferenceBinding caughtException = caughtExceptions[caughtIndex];
- for (int raisedIndex = 0; raisedIndex < raisedCount; raisedIndex++) {
- TypeBinding raisedException;
- if ((raisedException = raisedExceptions[raisedIndex]) != null) {
- switch (scope.compareTypes(raisedException, caughtException)) {
- case EqualOrMoreSpecific :
- exceptionContext.recordHandlingException(caughtException, flowInfo.unconditionalInits(), raisedException, location, locallyCaught[raisedIndex]); // was already definitely caught ?
- if (!locallyCaught[raisedIndex]){
- locallyCaught[raisedIndex] = true; // remember that this exception has been definitely caught
- remainingCount--;
- }
- break;
- case MoreGeneric :
- exceptionContext.recordHandlingException(caughtException, flowInfo.unconditionalInits(), raisedException, location, false); // was not caught already per construction
+ remainingCount = raisedCount;
+
+ // duplicate the array of raised exceptions since it will be updated
+ // (null replaces any handled exception)
+ System.arraycopy(
+ raisedExceptions,
+ 0,
+ (raisedExceptions = new TypeBinding[raisedCount]),
+ 0,
+ raisedCount);
+ FlowContext traversedContext = this;
+ while (traversedContext != null) {
+ AstNode sub;
+ if (((sub = traversedContext.subRoutine()) != null) && sub.cannotReturn()) {
+ // traversing a non-returning subroutine means that all unhandled
+ // exceptions will actually never get sent...
+ return;
+ }
+ // filter exceptions that are locally caught from the most enclosing
+ // try statement to the outer ones.
+ if (traversedContext instanceof ExceptionHandlingFlowContext) {
+ ExceptionHandlingFlowContext exceptionContext =
+ (ExceptionHandlingFlowContext) traversedContext;
+ ReferenceBinding[] caughtExceptions;
+ if ((caughtExceptions = exceptionContext.handledExceptions) != NoExceptions) {
+ int caughtCount = caughtExceptions.length;
+ boolean[] locallyCaught = new boolean[raisedCount]; // at most
+
+ for (int caughtIndex = 0; caughtIndex < caughtCount; caughtIndex++) {
+ ReferenceBinding caughtException = caughtExceptions[caughtIndex];
+ for (int raisedIndex = 0; raisedIndex < raisedCount; raisedIndex++) {
+ TypeBinding raisedException;
+ if ((raisedException = raisedExceptions[raisedIndex]) != null) {
+ switch (scope.compareTypes(raisedException, caughtException)) {
+ case EqualOrMoreSpecific :
+ exceptionContext.recordHandlingException(
+ caughtException,
+ flowInfo.unconditionalInits(),
+ raisedException,
+ location,
+ locallyCaught[raisedIndex]);
+ // was already definitely caught ?
+ if (!locallyCaught[raisedIndex]) {
+ locallyCaught[raisedIndex] = true;
+ // remember that this exception has been definitely caught
+ remainingCount--;
+ }
+ break;
+ case MoreGeneric :
+ exceptionContext.recordHandlingException(
+ caughtException,
+ flowInfo.unconditionalInits(),
+ raisedException,
+ location,
+ false);
+ // was not caught already per construction
+ }
}
}
}
- }
- // remove locally caught exceptions from the remaining ones
- for (int i = 0; i < raisedCount; i++) {
- if (locallyCaught[i]) {
- raisedExceptions[i] = null; // removed from the remaining ones.
+ // remove locally caught exceptions from the remaining ones
+ for (int i = 0; i < raisedCount; i++) {
+ if (locallyCaught[i]) {
+ raisedExceptions[i] = null; // removed from the remaining ones.
+ }
}
}
- }
- // method treatment for unchecked exceptions
- if (exceptionContext.isMethodContext){
- for (int i = 0; i < raisedCount; i++) {
- TypeBinding raisedException;
- if ((raisedException = raisedExceptions[i]) != null) {
- if (scope.areTypesCompatible(raisedException, scope.getJavaLangRuntimeException())
- || scope.areTypesCompatible(raisedException, scope.getJavaLangError())){
- remainingCount --;
- raisedExceptions[i] = null;
+ // method treatment for unchecked exceptions
+ if (exceptionContext.isMethodContext) {
+ for (int i = 0; i < raisedCount; i++) {
+ TypeBinding raisedException;
+ if ((raisedException = raisedExceptions[i]) != null) {
+ if (scope
+ .areTypesCompatible(raisedException, scope.getJavaLangRuntimeException())
+ || scope.areTypesCompatible(raisedException, scope.getJavaLangError())) {
+ remainingCount--;
+ raisedExceptions[i] = null;
+ }
}
- }
+ }
}
}
+ if (remainingCount == 0)
+ return;
+ traversedContext = traversedContext.parent;
+ }
+ // if reaches this point, then there are some remaining unhandled exception types.
+ for (int i = 0; i < raisedCount; i++) {
+ TypeBinding exception;
+ if ((exception = raisedExceptions[i]) != null) {
+ scope.problemReporter().unhandledException(exception, location, scope);
+ }
}
- if (remainingCount == 0)
- return;
- traversedContext = traversedContext.parent;
}
- // if reaches this point, then there are some remaining unhandled exception types.
- for (int i = 0; i < raisedCount; i++) {
- TypeBinding exception;
- if ((exception = raisedExceptions[i]) != null) {
- scope.problemReporter().unhandledException(exception, location, scope);
+ public void checkExceptionHandlers(
+ TypeBinding raisedException,
+ AstNode location,
+ FlowInfo flowInfo,
+ BlockScope scope) {
+
+ // LIGHT-VERSION OF THE EQUIVALENT WITH AN ARRAY OF EXCEPTIONS
+ // check that all the argument exception types are handled
+ // JDK Compatible implementation - when an exception type is thrown,
+ // all related catch blocks are marked as reachable... instead of those only
+ // until the point where it is safely handled (Smarter - see comment at the end)
+ FlowContext traversedContext = this;
+ while (traversedContext != null) {
+ AstNode sub;
+ if (((sub = traversedContext.subRoutine()) != null) && sub.cannotReturn()) {
+ // traversing a non-returning subroutine means that all unhandled
+ // exceptions will actually never get sent...
+ return;
+ }
+ // filter exceptions that are locally caught from the most enclosing
+ // try statement to the outer ones.
+ if (traversedContext instanceof ExceptionHandlingFlowContext) {
+ ExceptionHandlingFlowContext exceptionContext =
+ (ExceptionHandlingFlowContext) traversedContext;
+ ReferenceBinding[] caughtExceptions;
+ if ((caughtExceptions = exceptionContext.handledExceptions) != NoExceptions) {
+ boolean definitelyCaught = false;
+ for (int caughtIndex = 0, caughtCount = caughtExceptions.length;
+ caughtIndex < caughtCount;
+ caughtIndex++) {
+ ReferenceBinding caughtException = caughtExceptions[caughtIndex];
+ switch (scope.compareTypes(raisedException, caughtException)) {
+ case EqualOrMoreSpecific :
+ exceptionContext.recordHandlingException(
+ caughtException,
+ flowInfo.unconditionalInits(),
+ raisedException,
+ location,
+ definitelyCaught);
+ // was it already definitely caught ?
+ definitelyCaught = true;
+ break;
+ case MoreGeneric :
+ exceptionContext.recordHandlingException(
+ caughtException,
+ flowInfo.unconditionalInits(),
+ raisedException,
+ location,
+ false);
+ // was not caught already per construction
+ }
+ }
+ if (definitelyCaught)
+ return;
+ }
+ // method treatment for unchecked exceptions
+ if (exceptionContext.isMethodContext) {
+ if (scope
+ .areTypesCompatible(raisedException, scope.getJavaLangRuntimeException())
+ || scope.areTypesCompatible(raisedException, scope.getJavaLangError()))
+ return;
+ break; // not handled anywhere, thus jump to error handling
+ }
+ }
+ traversedContext = traversedContext.parent;
}
+ // if reaches this point, then there are some remaining unhandled exception types.
+ scope.problemReporter().unhandledException(raisedException, location, scope);
}
-}
-/*
-" - SMARTER VERSION -
-| unhandledExceptionTypes nameEnv traversedContext |
-
-someExceptionTypes isEmpty ifTrue: [^self].
-
-unhandledExceptionTypes := someExceptionTypes asOrderedCollection.
-nameEnv := scope enclosingMethod nameEnvironment.
-
-traversedContext := self.
-[traversedContext isNil] whileFalse: [| caughtExceptions sub |
-
-((sub := traversedContext subRoutine) notNil and: [sub cannotReturn])
-ifTrue: [
-" "Traversing a non-returning subroutine means that all unhandled exceptions will actually
-never get sent..." "
-^self].
-" "Filter exceptions that are locally caught from the most enclosing try statement to the outer ones." "
-(caughtExceptions := traversedContext handledExceptions) isNil
-ifFalse: [
-caughtExceptions do: [:handledExceptionAssoc | | handledException |
-handledException := handledExceptionAssoc key.
-unhandledExceptionTypes copy do: [:raisedException | | safe |
-" "Any exception recognized as being caught is removed from the exceptions list" "
-((safe := raisedException isCompatibleWith: handledException in: nameEnv)
-or: [handledException isCompatibleWith: raisedException in: nameEnv])
-ifTrue: [
-traversedContext
-recordInitializationInfo: initInfo
-onException: handledException.
-handledExceptionAssoc value: true.
-safe ifTrue: [unhandledExceptionTypes remove: raisedException]]]]].
-unhandledExceptionTypes isEmpty ifTrue: [^self].
-traversedContext := traversedContext parent].
-
-scope enclosingMethod errorInterface
-unexpectedExceptionsError: unhandledExceptionTypes
-from: invocationSite
-
-*/
-public void checkExceptionHandlers(TypeBinding raisedException, AstNode location, FlowInfo flowInfo, BlockScope scope) {
-
- // LIGHT-VERSION OF THE EQUIVALENT WITH AN ARRAY OF EXCEPTIONS
-
- // check that all the argument exception types are handled
- // JDK Compatible implementation - when an exception type is thrown,
- // all related catch blocks are marked as reachable... instead of those only
- // until the point where it is safely handled (Smarter - see comment at the end)
+ public Label continueLabel() {
+ return null;
+ }
- FlowContext traversedContext = this;
- while (traversedContext != null) {
- AstNode sub;
- if (((sub = traversedContext.subRoutine()) != null) && sub.cannotReturn()) {
- // traversing a non-returning subroutine means that all unhandled
- // exceptions will actually never get sent...
- return;
+ /*
+ * lookup through break labels
+ */
+ public FlowContext getTargetContextForBreakLabel(char[] labelName) {
+ FlowContext current = this, lastNonReturningSubRoutine = null;
+ while (current != null) {
+ if (current.isNonReturningContext()) {
+ lastNonReturningSubRoutine = current;
+ }
+ char[] currentLabelName;
+ if (((currentLabelName = current.labelName()) != null)
+ && CharOperation.equals(currentLabelName, labelName)) {
+ if (lastNonReturningSubRoutine == null) {
+ return current;
+ } else {
+ return lastNonReturningSubRoutine;
+ }
+ }
+ current = current.parent;
}
+ // not found
+ return null;
+ }
- // filter exceptions that are locally caught from the most enclosing
- // try statement to the outer ones.
- if (traversedContext instanceof ExceptionHandlingFlowContext) {
- ExceptionHandlingFlowContext exceptionContext = (ExceptionHandlingFlowContext) traversedContext;
- ReferenceBinding[] caughtExceptions;
- if ((caughtExceptions = exceptionContext.handledExceptions) != NoExceptions) {
- boolean definitelyCaught = false;
- for (int caughtIndex = 0, caughtCount = caughtExceptions.length; caughtIndex < caughtCount; caughtIndex++) {
- ReferenceBinding caughtException = caughtExceptions[caughtIndex];
- switch (scope.compareTypes(raisedException, caughtException)) {
- case EqualOrMoreSpecific :
- exceptionContext.recordHandlingException(
- caughtException,
- flowInfo.unconditionalInits(),
- raisedException,
- location,
- definitelyCaught); // was it already definitely caught ?
- definitelyCaught = true;
- break;
- case MoreGeneric :
- exceptionContext.recordHandlingException(
- caughtException,
- flowInfo.unconditionalInits(),
- raisedException,
- location,
- false); // was not caught already per construction
- }
+ /*
+ * lookup through continue labels
+ */
+ public FlowContext getTargetContextForContinueLabel(char[] labelName) {
+ FlowContext current = this,
+ lastContinuable = null,
+ lastNonReturningSubRoutine = null;
+ while (current != null) {
+ if (current.isNonReturningContext()) {
+ lastNonReturningSubRoutine = current;
+ } else {
+ if (current.isContinuable()) {
+ lastContinuable = current;
}
- if (definitelyCaught) return;
}
- // method treatment for unchecked exceptions
- if (exceptionContext.isMethodContext){
- if (scope.areTypesCompatible(raisedException, scope.getJavaLangRuntimeException())
- || scope.areTypesCompatible(raisedException, scope.getJavaLangError()))
- return;
- break; // not handled anywhere, thus jump to error handling
+ char[] currentLabelName;
+ if (((currentLabelName = current.labelName()) != null)
+ && CharOperation.equals(currentLabelName, labelName)) {
+ if ((lastContinuable != null)
+ && (current.associatedNode.concreteStatement()
+ == lastContinuable.associatedNode)) {
+ if (lastNonReturningSubRoutine == null) {
+ return lastContinuable;
+ } else {
+ return lastNonReturningSubRoutine;
+ }
+ } else {
+ // label is found, but not a continuable location
+ return NotContinuableContext;
+ }
}
+ current = current.parent;
}
- traversedContext = traversedContext.parent;
+ // not found
+ return null;
}
- // if reaches this point, then there are some remaining unhandled exception types.
- scope.problemReporter().unhandledException(raisedException, location, scope);
-}
-public Label continueLabel() {
- return null;
-}
-public FlowContext getTargetContextForBreakLabel(char[] labelName) {
-
- // lookup through break labels
-
- FlowContext current = this, lastNonReturningSubRoutine = null;
- while (current != null) {
- if (current.isNonReturningContext()) {
- lastNonReturningSubRoutine = current;
- }
- char[] currentLabelName;
- if (((currentLabelName = current.labelName()) != null)
- && CharOperation.equals(currentLabelName, labelName)) {
- if (lastNonReturningSubRoutine == null) {
- return current;
- } else {
- return lastNonReturningSubRoutine;
+ /*
+ * lookup a default break through breakable locations
+ */
+ public FlowContext getTargetContextForDefaultBreak() {
+ FlowContext current = this, lastNonReturningSubRoutine = null;
+ while (current != null) {
+ if (current.isNonReturningContext()) {
+ lastNonReturningSubRoutine = current;
+ }
+ if (current.isBreakable()) {
+ if (lastNonReturningSubRoutine == null) {
+ return current;
+ } else {
+ return lastNonReturningSubRoutine;
+ }
}
+ current = current.parent;
}
- current = current.parent;
+ // not found
+ return null;
}
- // not found
- return null;
-}
-public FlowContext getTargetContextForContinueLabel(char[] labelName) {
-
- // lookup through continue labels
-
- FlowContext current = this, lastContinuable = null, lastNonReturningSubRoutine = null;
- while (current != null) {
- if (current.isNonReturningContext()) {
- lastNonReturningSubRoutine = current;
- } else {
- if (current.isContinuable()) {
- lastContinuable = current;
+ /*
+ * lookup a default continue amongst continuable locations
+ */
+ public FlowContext getTargetContextForDefaultContinue() {
+ FlowContext current = this, lastNonReturningSubRoutine = null;
+ while (current != null) {
+ if (current.isNonReturningContext()) {
+ lastNonReturningSubRoutine = current;
}
- }
- char[] currentLabelName;
- if (((currentLabelName = current.labelName()) != null)
- && CharOperation.equals(currentLabelName, labelName)) {
- if ((lastContinuable != null) && (current.associatedNode.concreteStatement() == lastContinuable.associatedNode)) {
+ if (current.isContinuable()) {
if (lastNonReturningSubRoutine == null) {
- return lastContinuable;
+ return current;
} else {
return lastNonReturningSubRoutine;
}
- } else {
- // label is found, but not a continuable location
- return NotContinuableContext;
}
+ current = current.parent;
}
- current = current.parent;
+ // not found
+ return null;
}
- // not found
- return null;
-}
-public FlowContext getTargetContextForDefaultBreak() {
+ public String individualToString() {
+ return "Flow context"; //$NON-NLS-1$
+ }
- // lookup through break labels
+ public FlowInfo initsOnBreak() {
+ return FlowInfo.DeadEnd;
+ }
- FlowContext current = this, lastNonReturningSubRoutine = null;
- while (current != null) {
- if (current.isNonReturningContext()) {
- lastNonReturningSubRoutine = current;
- }
- if (current.isBreakable()) {
- if (lastNonReturningSubRoutine == null) {
- return current;
- } else {
- return lastNonReturningSubRoutine;
- }
- }
- current = current.parent;
+ public boolean isBreakable() {
+ return false;
}
- // not found
- return null;
-}
-public FlowContext getTargetContextForDefaultContinue() {
+ public boolean isContinuable() {
+ return false;
+ }
- // lookup through continue labels
+ public boolean isNonReturningContext() {
+ return false;
+ }
+ public boolean isSubRoutine() {
+ return false;
+ }
- FlowContext current = this, lastNonReturningSubRoutine = null;
- while (current != null) {
- if (current.isNonReturningContext()) {
- lastNonReturningSubRoutine = current;
- }
- if (current.isContinuable()) {
- if (lastNonReturningSubRoutine == null) {
- return current;
- } else {
- return lastNonReturningSubRoutine;
- }
- }
- current = current.parent;
+ public char[] labelName() {
+ return null;
}
- // not found
- return null;
-}
-public String individualToString(){
- return "Flow context"; //$NON-NLS-1$
-}
-public FlowInfo initsOnBreak() {
- return FlowInfo.DeadEnd;
-}
-public boolean isBreakable() {
- return false;
-}
-public boolean isContinuable() {
- return false;
-}
-public boolean isNonReturningContext() {
- return false;
-}
-public boolean isSubRoutine() {
- return false;
-}
-public char[] labelName() {
- return null;
-}
-public void recordBreakFrom(FlowInfo flowInfo) {
-}
-public void recordContinueFrom(FlowInfo flowInfo) {
-}
-boolean recordFinalAssignment(VariableBinding variable, Reference finalReference) {
- return true; // keep going
-}
-public void recordReturnFrom(UnconditionalFlowInfo flowInfo) {
-}
-public void recordSettingFinal(VariableBinding variable, Reference finalReference) {
+ public void recordBreakFrom(FlowInfo flowInfo) {
+ }
- // for initialization inside looping statement that effectively loops
+ public void recordContinueFrom(FlowInfo flowInfo) {
+ }
- FlowContext context = this;
- while (context != null) {
- if (!context.recordFinalAssignment(variable, finalReference)){
- break; // no need to keep going
+ boolean recordFinalAssignment(
+ VariableBinding variable,
+ Reference finalReference) {
+ return true; // keep going
+ }
+
+ public void recordReturnFrom(UnconditionalFlowInfo flowInfo) {
+ }
+
+ public void recordSettingFinal(
+ VariableBinding variable,
+ Reference finalReference) {
+ // for initialization inside looping statement that effectively loops
+ FlowContext context = this;
+ while (context != null) {
+ if (!context.recordFinalAssignment(variable, finalReference)) {
+ break; // no need to keep going
+ }
+ context = context.parent;
}
- context = context.parent;
}
-}
-void removeFinalAssignmentIfAny(Reference reference) {
-}
-public AstNode subRoutine() {
- return null;
-}
-public String toString(){
- StringBuffer buffer = new StringBuffer();
- FlowContext current = this;
- int parentsCount = 0;
- while ((current = current.parent) != null){ parentsCount++; }
-
- FlowContext[] parents = new FlowContext[parentsCount+1];
- current = this;
- int index = parentsCount;
- while (index >= 0) {
- parents[index--] = current;
- current = current.parent;
+ void removeFinalAssignmentIfAny(Reference reference) {
}
- for(int i = 0; i < parentsCount; i++){
- for(int j = 0; j < i; j++) buffer.append('\t');
- buffer.append(parents[i].individualToString()).append('\n');
+ public AstNode subRoutine() {
+ return null;
+ }
+
+ public String toString() {
+ StringBuffer buffer = new StringBuffer();
+ FlowContext current = this;
+ int parentsCount = 0;
+ while ((current = current.parent) != null) {
+ parentsCount++;
+ }
+ FlowContext[] parents = new FlowContext[parentsCount + 1];
+ current = this;
+ int index = parentsCount;
+ while (index >= 0) {
+ parents[index--] = current;
+ current = current.parent;
+ }
+ for (int i = 0; i < parentsCount; i++) {
+ for (int j = 0; j < i; j++)
+ buffer.append('\t');
+ buffer.append(parents[i].individualToString()).append('\n');
+ }
+ buffer.append('*');
+ for (int j = 0; j < parentsCount + 1; j++)
+ buffer.append('\t');
+ buffer.append(individualToString()).append('\n');
+ return buffer.toString();
}
- buffer.append('*');
- for(int j = 0; j < parentsCount+1; j++) buffer.append('\t');
- buffer.append(individualToString()).append('\n');
- return buffer.toString();
-}
-}
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LabelFlowContext.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LabelFlowContext.java
index 7a20c5609f..f7bddf772a 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LabelFlowContext.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LabelFlowContext.java
@@ -17,30 +17,35 @@ import org.eclipse.jdt.internal.compiler.util.*;
*/
public class LabelFlowContext extends SwitchFlowContext {
public char[] labelName;
-public LabelFlowContext(FlowContext parent, AstNode associatedNode, char[] labelName, Label breakLabel, BlockScope scope){
-
- super(parent, associatedNode, breakLabel);
- this.labelName = labelName;
- checkLabelValidity(scope);
-}
-void checkLabelValidity(BlockScope scope) {
-
- // check if label was already defined above
+ public LabelFlowContext(
+ FlowContext parent,
+ AstNode associatedNode,
+ char[] labelName,
+ Label breakLabel,
+ BlockScope scope) {
+ super(parent, associatedNode, breakLabel);
+ this.labelName = labelName;
+ checkLabelValidity(scope);
+ }
- FlowContext current = parent;
- while (current != null) {
- char[] currentLabelName;
- if (((currentLabelName = current.labelName()) != null)
- && CharOperation.equals(currentLabelName, labelName)) {
- scope.problemReporter().alreadyDefinedLabel(labelName, associatedNode);
+ void checkLabelValidity(BlockScope scope) {
+ // check if label was already defined above
+ FlowContext current = parent;
+ while (current != null) {
+ char[] currentLabelName;
+ if (((currentLabelName = current.labelName()) != null)
+ && CharOperation.equals(currentLabelName, labelName)) {
+ scope.problemReporter().alreadyDefinedLabel(labelName, associatedNode);
+ }
+ current = current.parent;
}
- current = current.parent;
}
-}
-public String individualToString(){
- return "Label flow context [label:"+String.valueOf(labelName)+"]"; //$NON-NLS-2$ //$NON-NLS-1$
-}
-public char[] labelName() {
- return labelName;
-}
-}
+
+ public String individualToString() {
+ return "Label flow context [label:" + String.valueOf(labelName) + "]"; //$NON-NLS-2$ //$NON-NLS-1$
+ }
+
+ public char[] labelName() {
+ return labelName;
+ }
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LoopingFlowContext.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LoopingFlowContext.java
index 77032ef588..09c1ef1e1a 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LoopingFlowContext.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/LoopingFlowContext.java
@@ -18,91 +18,122 @@ public class LoopingFlowContext extends SwitchFlowContext {
public Label continueLabel;
public UnconditionalFlowInfo initsOnContinue = FlowInfo.DeadEnd;
Reference finalAssignments[];
- VariableBinding finalVariables[];
+ VariableBinding finalVariables[];
int assignCount = 0;
Scope associatedScope;
-public LoopingFlowContext(FlowContext parent, AstNode associatedNode, Label breakLabel, Label continueLabel, Scope associatedScope){
- super(parent, associatedNode,breakLabel);
- this.continueLabel = continueLabel;
- this.associatedScope = associatedScope;
-}
-public void complainOnFinalAssignmentsInLoop(BlockScope scope, FlowInfo flowInfo) {
- for (int i = 0; i < assignCount; i++) {
- VariableBinding variable;
- if ((variable = finalVariables[i]) != null) {
- boolean complained; // remember if have complained on this final assignment
- if (variable instanceof FieldBinding) {
- if (complained = flowInfo.isPotentiallyAssigned((FieldBinding) variable)) {
- scope.problemReporter().duplicateInitializationOfBlankFinalField((FieldBinding) variable, (NameReference) finalAssignments[i]);
- }
- } else {
- if (complained = flowInfo.isPotentiallyAssigned((LocalVariableBinding) variable)) {
- scope.problemReporter().duplicateInitializationOfFinalLocal((LocalVariableBinding) variable, (NameReference) finalAssignments[i]);
+ public LoopingFlowContext(
+ FlowContext parent,
+ AstNode associatedNode,
+ Label breakLabel,
+ Label continueLabel,
+ Scope associatedScope) {
+ super(parent, associatedNode, breakLabel);
+ this.continueLabel = continueLabel;
+ this.associatedScope = associatedScope;
+ }
+
+ public void complainOnFinalAssignmentsInLoop(
+ BlockScope scope,
+ FlowInfo flowInfo) {
+ for (int i = 0; i < assignCount; i++) {
+ VariableBinding variable;
+ if ((variable = finalVariables[i]) != null) {
+ boolean complained; // remember if have complained on this final assignment
+ if (variable instanceof FieldBinding) {
+ if (complained = flowInfo.isPotentiallyAssigned((FieldBinding) variable)) {
+ scope.problemReporter().duplicateInitializationOfBlankFinalField(
+ (FieldBinding) variable,
+ (NameReference) finalAssignments[i]);
+ }
+ } else {
+ if (complained =
+ flowInfo.isPotentiallyAssigned((LocalVariableBinding) variable)) {
+ scope.problemReporter().duplicateInitializationOfFinalLocal(
+ (LocalVariableBinding) variable,
+ (NameReference) finalAssignments[i]);
+ }
}
- }
- // any reference reported at this level is removed from the parent context where it
- // could also be reported again
- if (complained) {
- FlowContext context = parent;
- while (context != null) {
- context.removeFinalAssignmentIfAny(finalAssignments[i]);
- context = context.parent;
+ // any reference reported at this level is removed from the parent context where it
+ // could also be reported again
+ if (complained) {
+ FlowContext context = parent;
+ while (context != null) {
+ context.removeFinalAssignmentIfAny(finalAssignments[i]);
+ context = context.parent;
+ }
}
}
}
}
-}
-public Label continueLabel() {
- return continueLabel;
-}
-public String individualToString(){
- return "Looping flow context"; //$NON-NLS-1$
-}
-public boolean isContinuable() {
- return true;
-}
-public boolean isContinuedTo() {
- return initsOnContinue != FlowInfo.DeadEnd;
-}
-public void recordContinueFrom(FlowInfo flowInfo) {
- if (initsOnContinue == FlowInfo.DeadEnd) {
- initsOnContinue = flowInfo.copy().unconditionalInits();
- } else {
- // ignore if not really reachable (1FKEKRP)
- if (flowInfo.isFakeReachable())
- return;
- initsOnContinue.mergedWith(flowInfo.unconditionalInits());
- };
-}
-boolean recordFinalAssignment(VariableBinding binding, Reference finalAssignment) {
- // do not consider variables which are defined inside this loop
- if (binding instanceof LocalVariableBinding) {
- Scope scope = ((LocalVariableBinding) binding).declaringScope;
- while ((scope = scope.parent) != null) {
- if (scope == associatedScope) return false;
+ public Label continueLabel() {
+ return continueLabel;
+ }
+
+ public String individualToString() {
+ return "Looping flow context"; //$NON-NLS-1$
+ }
+
+ public boolean isContinuable() {
+ return true;
+ }
+
+ public boolean isContinuedTo() {
+ return initsOnContinue != FlowInfo.DeadEnd;
+ }
+
+ public void recordContinueFrom(FlowInfo flowInfo) {
+ if (initsOnContinue == FlowInfo.DeadEnd) {
+ initsOnContinue = flowInfo.copy().unconditionalInits();
+ } else {
+ // ignore if not really reachable (1FKEKRP)
+ if (flowInfo.isFakeReachable())
+ return;
+ initsOnContinue.mergedWith(flowInfo.unconditionalInits());
+ };
+ }
+
+ boolean recordFinalAssignment(
+ VariableBinding binding,
+ Reference finalAssignment) {
+ // do not consider variables which are defined inside this loop
+ if (binding instanceof LocalVariableBinding) {
+ Scope scope = ((LocalVariableBinding) binding).declaringScope;
+ while ((scope = scope.parent) != null) {
+ if (scope == associatedScope)
+ return false;
+ }
}
+ if (assignCount == 0) {
+ finalAssignments = new Reference[5];
+ finalVariables = new VariableBinding[5];
+ } else {
+ if (assignCount == finalAssignments.length)
+ System.arraycopy(
+ finalAssignments,
+ 0,
+ (finalAssignments = new Reference[assignCount * 2]),
+ 0,
+ assignCount);
+ System.arraycopy(
+ finalVariables,
+ 0,
+ (finalVariables = new VariableBinding[assignCount * 2]),
+ 0,
+ assignCount);
+ };
+ finalAssignments[assignCount] = finalAssignment;
+ finalVariables[assignCount++] = binding;
+ return true;
}
- if (assignCount == 0) {
- finalAssignments = new Reference[5];
- finalVariables = new VariableBinding[5];
- } else {
- if (assignCount == finalAssignments.length)
- System.arraycopy(finalAssignments, 0, (finalAssignments = new Reference[assignCount * 2]), 0, assignCount);
- System.arraycopy(finalVariables, 0, (finalVariables = new VariableBinding[assignCount * 2]), 0, assignCount);
- };
- finalAssignments[assignCount] = finalAssignment;
- finalVariables[assignCount++] = binding;
- return true;
-}
-void removeFinalAssignmentIfAny(Reference reference) {
- for (int i = 0; i < assignCount; i++) {
- if (finalAssignments[i] == reference) {
- finalAssignments[i] = null;
- finalVariables[i] = null;
- return;
+ void removeFinalAssignmentIfAny(Reference reference) {
+ for (int i = 0; i < assignCount; i++) {
+ if (finalAssignments[i] == reference) {
+ finalAssignments[i] = null;
+ finalVariables[i] = null;
+ return;
+ }
}
}
-}
-}
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/SwitchFlowContext.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/SwitchFlowContext.java
index 9d44fbdf04..7d6c523c90 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/SwitchFlowContext.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/flow/SwitchFlowContext.java
@@ -17,30 +17,35 @@ import org.eclipse.jdt.internal.compiler.problem.*;
public class SwitchFlowContext extends FlowContext {
public Label breakLabel;
public UnconditionalFlowInfo initsOnBreak = FlowInfo.DeadEnd;
-/**
- *
- */
-public SwitchFlowContext(FlowContext parent, AstNode associatedNode, Label breakLabel) {
- super(parent, associatedNode);
- this.breakLabel = breakLabel;
-}
-public Label breakLabel() {
- return breakLabel;
-}
-public String individualToString(){
- return "Switch flow context"; //$NON-NLS-1$
-}
-public boolean isBreakable() {
- return true;
-}
-public void recordBreakFrom(FlowInfo flowInfo) {
+
+ public SwitchFlowContext(
+ FlowContext parent,
+ AstNode associatedNode,
+ Label breakLabel) {
+ super(parent, associatedNode);
+ this.breakLabel = breakLabel;
+ }
+
+ public Label breakLabel() {
+ return breakLabel;
+ }
+
+ public String individualToString() {
+ return "Switch flow context"; //$NON-NLS-1$
+ }
+
+ public boolean isBreakable() {
+ return true;
+ }
- if (initsOnBreak == FlowInfo.DeadEnd) {
- initsOnBreak = flowInfo.copy().unconditionalInits();
- } else {
- // ignore if not really reachable (1FKEKRP)
- if (flowInfo.isFakeReachable()) return;
- initsOnBreak.mergedWith(flowInfo.unconditionalInits());
- };
-}
-}
+ public void recordBreakFrom(FlowInfo flowInfo) {
+ if (initsOnBreak == FlowInfo.DeadEnd) {
+ initsOnBreak = flowInfo.copy().unconditionalInits();
+ } else {
+ // ignore if not really reachable (1FKEKRP)
+ if (flowInfo.isFakeReachable())
+ return;
+ initsOnBreak.mergedWith(flowInfo.unconditionalInits());
+ };
+ }
+} \ No newline at end of file
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/impl/Constant.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/impl/Constant.java
index 8f05951b88..1237369e10 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/impl/Constant.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/impl/Constant.java
@@ -225,9 +225,9 @@ public static final Constant computeConstantOperation(Constant cst, int id, int
//the result should be availbale with not runtime error
switch (operator) {
- case NOT : if ( cst.booleanValue() == true ) return Constant.fromValue(false);
- return Constant.fromValue(true);
- case PLUS : return cst ; //apriori we do not need to clone it
+ case NOT :
+ return Constant.fromValue(!cst.booleanValue());
+ case PLUS : return cst ;
case MINUS : //the two special -9223372036854775808L and -2147483648 are inlined at parseTime
switch (id){
case T_float : float f ;
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/CompilationUnitScope.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/CompilationUnitScope.java
index 230c76a9ec..411c72a502 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/CompilationUnitScope.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/CompilationUnitScope.java
@@ -106,7 +106,9 @@ void buildTypeBindings() {
}
if ((typeDecl.modifiers & AccPublic) != 0) {
- if (!CharOperation.equals(referenceContext.getMainTypeName(), typeDecl.name)) {
+ char[] mainTypeName;
+ if ((mainTypeName = referenceContext.getMainTypeName()) != null // mainTypeName == null means that implementor of ICompilationUnit decided to return null
+ && !CharOperation.equals(mainTypeName, typeDecl.name)) {
problemReporter().publicClassMustMatchFileName(referenceContext, typeDecl);
continue nextType;
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java
index 7dfcb9ec9a..5ae652128b 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java
@@ -122,6 +122,9 @@ public final boolean canBeSeenBy(InvocationSite invocationSite, Scope scope) {
*/
public final boolean canBeSeenBy(TypeBinding receiverType, InvocationSite invocationSite, Scope scope) {
+ return this.canBeSeenBy(receiverType,invocationSite.isSuperAccess(),scope);
+}
+public final boolean canBeSeenBy(TypeBinding receiverType, boolean isSuperAccess, Scope scope) {
if (isPublic()) return true;
SourceTypeBinding invocationType = scope.enclosingSourceType();
@@ -135,7 +138,7 @@ public final boolean canBeSeenBy(TypeBinding receiverType, InvocationSite invoca
if (invocationType == declaringClass) return true;
if (invocationType.fPackage == declaringClass.fPackage) return true;
if (declaringClass.isSuperclassOf(invocationType)) {
- if (invocationSite.isSuperAccess()) return true;
+ if (isSuperAccess) return true;
// receiverType can be an array binding in one case... see if you can change it
if (receiverType instanceof ArrayBinding)
return false;
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredField.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredField.java
index c1efacb2d4..a894082892 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredField.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredField.java
@@ -104,6 +104,7 @@ public FieldDeclaration updatedFieldDeclaration(){
((AnonymousLocalTypeDeclaration)this.anonymousTypes[i].updatedTypeDeclaration()).allocation;
}
}
+ if (this.anonymousTypeCount > 0) fieldDeclaration.bits |= AstNode.HasLocalTypeMASK;
}
return fieldDeclaration;
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredInitializer.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredInitializer.java
index 337292544a..b8b9448da7 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredInitializer.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredInitializer.java
@@ -176,6 +176,8 @@ public FieldDeclaration updatedFieldDeclaration(){
if (block != null){
((Initializer)fieldDeclaration).block = block;
}
+ if (this.localTypeCount > 0) fieldDeclaration.bits |= AstNode.HasLocalTypeMASK;
+
}
return fieldDeclaration;
}
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredMethod.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredMethod.java
index 49b642e9b9..790bd08f5a 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredMethod.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/RecoveredMethod.java
@@ -232,6 +232,7 @@ public AbstractMethodDeclaration updatedMethodDeclaration(){
}
}
}
+ if (localTypeCount > 0) methodDeclaration.bits |= AstNode.HasLocalTypeMASK;
return methodDeclaration;
}
/*
diff --git a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/util/Util.java b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/util/Util.java
index fe7748393d..78b9978b33 100644
--- a/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/util/Util.java
+++ b/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/util/Util.java
@@ -7,6 +7,8 @@ package org.eclipse.jdt.internal.compiler.util;
import java.util.Locale;
import java.util.MissingResourceException;
import java.util.ResourceBundle;
+import java.io.*;
+import java.util.zip.*;
public class Util {
/* Bundle containing messages */
@@ -86,6 +88,172 @@ public static String bind(String id) {
public static void relocalize() {
bundle = ResourceBundle.getBundle(bundleName, Locale.getDefault());
}
+/**
+ * Returns the given bytes as a char array.
+ */
+public static char[] bytesToChar(byte[] bytes) throws IOException {
+
+ return getInputStreamAsCharArray(new ByteArrayInputStream(bytes), bytes.length);
+
+}
+/**
+ * Returns the contents of the given file as a byte array.
+ * @throws IOException if a problem occured reading the file.
+ */
+public static byte[] getFileByteContent(File file) throws IOException {
+ InputStream stream = null;
+ try {
+ stream = new BufferedInputStream(new FileInputStream(file));
+ return getInputStreamAsByteArray(stream, (int) file.length());
+ } finally {
+ if (stream != null) {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
+ }
+}
+/**
+ * Returns the contents of the given file as a char array.
+ * @throws IOException if a problem occured reading the file.
+ */
+public static char[] getFileCharContent(File file) throws IOException {
+ InputStream stream = null;
+ try {
+ stream = new BufferedInputStream(new FileInputStream(file));
+ return Util.getInputStreamAsCharArray(stream, (int) file.length());
+ } finally {
+ if (stream != null) {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
+ }
+}
+/**
+ * Returns the given input stream's contents as a byte array.
+ * If a length is specified (ie. if length != -1), only length bytes
+ * are returned. Otherwise all bytes in the stream are returned.
+ * Note this doesn't close the stream.
+ * @throws IOException if a problem occured reading the stream.
+ */
+public static byte[] getInputStreamAsByteArray(InputStream stream, int length) throws IOException {
+ byte[] contents;
+ if (length == -1) {
+ contents = new byte[0];
+ int contentsLength = 0;
+ int bytesRead = -1;
+ do {
+ int available= stream.available();
+
+ // resize contents if needed
+ if (contentsLength + available > contents.length) {
+ System.arraycopy(contents, 0, contents = new byte[contentsLength + available], 0, contentsLength);
+ }
+
+ // read as many bytes as possible
+ bytesRead = stream.read(contents, contentsLength, available);
+
+ if (bytesRead > 0) {
+ // remember length of contents
+ contentsLength += bytesRead;
+ }
+ } while (bytesRead > 0);
+
+ // resize contents if necessary
+ if (contentsLength < contents.length) {
+ System.arraycopy(contents, 0, contents = new byte[contentsLength], 0, contentsLength);
+ }
+ } else {
+ contents = new byte[length];
+ int len = 0;
+ int readSize = 0;
+ while ((readSize != -1) && (len != length)) {
+ // See PR 1FMS89U
+ // We record first the read size. In this case len is the actual read size.
+ len += readSize;
+ readSize = stream.read(contents, len, length - len);
+ }
+ }
+
+ return contents;
+}
+/**
+ * Returns the given input stream's contents as a character array.
+ * If a length is specified (ie. if length != -1), only length chars
+ * are returned. Otherwise all chars in the stream are returned.
+ * Note this doesn't close the stream.
+ * @throws IOException if a problem occured reading the stream.
+ */
+public static char[] getInputStreamAsCharArray(InputStream stream, int length) throws IOException {
+ InputStreamReader reader= null;
+ reader= new InputStreamReader(stream);
+ char[] contents;
+ if (length == -1) {
+ contents = new char[0];
+ int contentsLength = 0;
+ int charsRead = -1;
+ do {
+ int available= stream.available();
+
+ // resize contents if needed
+ if (contentsLength + available > contents.length) {
+ System.arraycopy(contents, 0, contents = new char[contentsLength + available], 0, contentsLength);
+ }
+
+ // read as many chars as possible
+ charsRead = reader.read(contents, contentsLength, available);
+
+ if (charsRead > 0) {
+ // remember length of contents
+ contentsLength += charsRead;
+ }
+ } while (charsRead > 0);
+
+ // resize contents if necessary
+ if (contentsLength < contents.length) {
+ System.arraycopy(contents, 0, contents = new char[contentsLength], 0, contentsLength);
+ }
+ } else {
+ contents = new char[length];
+ int len = 0;
+ int readSize = 0;
+ while ((readSize != -1) && (len != length)) {
+ // See PR 1FMS89U
+ // We record first the read size. In this case len is the actual read size.
+ len += readSize;
+ readSize = reader.read(contents, len, length - len);
+ }
+ // See PR 1FMS89U
+ // Now we need to resize in case the default encoding used more than one byte for each
+ // character
+ if (len != length)
+ System.arraycopy(contents, 0, (contents = new char[len]), 0, len);
+ }
+
+ return contents;
+}
+/**
+ * Returns the contents of the given zip entry as a byte array.
+ * @throws IOException if a problem occured reading the zip entry.
+ */
+public static byte[] getZipEntryByteContent(ZipEntry ze, ZipFile zip) throws IOException {
+ InputStream stream = null;
+ byte classFileBytes[] = null;
+ try {
+ stream = new BufferedInputStream(zip.getInputStream(ze));
+ return getInputStreamAsByteArray(stream, (int) ze.getSize());
+ } finally {
+ if (stream != null) {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
+ }
+}
public static void main(String[] arg){
System.out.println(bind("test")); //$NON-NLS-1$
}
diff --git a/org.eclipse.jdt.core/eval/org/eclipse/jdt/internal/eval/CodeSnippetParser.java b/org.eclipse.jdt.core/eval/org/eclipse/jdt/internal/eval/CodeSnippetParser.java
index 0a79eabce9..be01278dcf 100644
--- a/org.eclipse.jdt.core/eval/org/eclipse/jdt/internal/eval/CodeSnippetParser.java
+++ b/org.eclipse.jdt.core/eval/org/eclipse/jdt/internal/eval/CodeSnippetParser.java
@@ -68,6 +68,9 @@ protected void classInstanceCreation(boolean alwaysQualified) {
anonymousTypeDeclaration.declarationSourceEnd = endStatementPosition;
astPtr--;
astLengthPtr--;
+
+ // mark fields and initializer with local type mark if needed
+ markFieldsWithLocalType(anonymousTypeDeclaration);
}
}
protected void consumeClassDeclaration() {
@@ -88,6 +91,7 @@ protected void consumeClassHeaderName() {
} else {
// Record that the block has a declaration for local types
typeDecl = new LocalTypeDeclaration();
+ markCurrentMethodWithLocalType();
blockReal();
}
@@ -165,6 +169,7 @@ protected void consumeInterfaceHeaderName() {
} else {
// Record that the block has a declaration for local types
typeDecl = new LocalTypeDeclaration();
+ markCurrentMethodWithLocalType();
blockReal();
}
@@ -563,7 +568,7 @@ protected NameReference getUnspecifiedReferenceOptimized() {
identifierStack[identifierPtr],
identifierPositionStack[identifierPtr--],
this.evaluationContext);
- ref.bits &= ~NameReference.RestrictiveFlagMASK;
+ ref.bits &= ~AstNode.RestrictiveFlagMASK;
ref.bits |= LOCAL | FIELD;
return ref;
}
@@ -582,7 +587,7 @@ protected NameReference getUnspecifiedReferenceOptimized() {
(int) (identifierPositionStack[identifierPtr + 1] >> 32), // sourceStart
(int) identifierPositionStack[identifierPtr + length],
evaluationContext); // sourceEnd
- ref.bits &= ~NameReference.RestrictiveFlagMASK;
+ ref.bits &= ~AstNode.RestrictiveFlagMASK;
ref.bits |= LOCAL | FIELD;
return ref;
} else {
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaProject.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaProject.java
index c3b890234a..a7c772be0e 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaProject.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaProject.java
@@ -836,14 +836,10 @@ public String[] getRequiredProjectNames() throws JavaModelException {
public String getSharedProperty(QualifiedName key) throws CoreException {
String property = null;
- try {
- String propertyFileName= computeSharedPropertyFileName(key);
- IFile rscFile = getProject().getFile(propertyFileName);
- if (rscFile.exists()){
- InputStream input = rscFile.getContents(true);
- property = new String(Util.readContentsAsBytes(input));
- }
- } catch (IOException e) {
+ String propertyFileName= computeSharedPropertyFileName(key);
+ IFile rscFile = getProject().getFile(propertyFileName);
+ if (rscFile.exists()){
+ property = new String(Util.getResourceContentsAsByteArray(rscFile));
}
return property;
}
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Openable.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Openable.java
index 46aae5995e..da4a52c4b4 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Openable.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Openable.java
@@ -97,7 +97,11 @@ protected void codeComplete(org.eclipse.jdt.internal.compiler.env.ICompilationUn
if (requestor == null) {
throw new IllegalArgumentException(Util.bind("codeAssist.nullRequestor")); //$NON-NLS-1$
}
- if (position < -1 || position > getBuffer().getLength()) {
+ IBuffer buffer = getBuffer();
+ if (buffer == null) {
+ return;
+ }
+ if (position < -1 || position > buffer.getLength()) {
throw new JavaModelException(new JavaModelStatus(IJavaModelStatusConstants.INDEX_OUT_OF_BOUNDS));
}
SearchableEnvironment environment = (SearchableEnvironment) ((JavaProject) getJavaProject()).getSearchableNameEnvironment();
@@ -125,7 +129,11 @@ protected void codeSelect(org.eclipse.jdt.internal.compiler.env.ICompilationUnit
return;
}
- int end= getBuffer().getLength();
+ IBuffer buffer = getBuffer();
+ if (buffer == null) {
+ return;
+ }
+ int end= buffer.getLength();
if (offset < 0 || length < 0 || offset + length > end ) {
throw new JavaModelException(new JavaModelStatus(IJavaModelStatusConstants.INDEX_OUT_OF_BOUNDS));
}
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Util.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Util.java
index 3c65b31fa6..1c94bed62c 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Util.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/Util.java
@@ -4,6 +4,11 @@ package org.eclipse.jdt.internal.core;
* (c) Copyright IBM Corp. 2000, 2001.
* All Rights Reserved.
*/
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.runtime.CoreException;
+
+import org.eclipse.jdt.core.JavaModelException;
+import org.eclipse.jdt.core.IJavaModelStatusConstants;
import org.eclipse.jdt.internal.compiler.util.CharOperation;
import java.io.*;
@@ -392,6 +397,48 @@ public static int getParameterCount(char[] sig) {
}
return count;
}
+/**
+ * Returns the given file's contents as a byte array.
+ */
+public static byte[] getResourceContentsAsByteArray(IFile file) throws JavaModelException {
+ InputStream stream= null;
+ try {
+ stream = new BufferedInputStream(file.getContents(true));
+ } catch (CoreException e) {
+ throw new JavaModelException(e);
+ }
+ try {
+ return org.eclipse.jdt.internal.compiler.util.Util.getInputStreamAsByteArray(stream, -1);
+ } catch (IOException e) {
+ throw new JavaModelException(e, IJavaModelStatusConstants.IO_EXCEPTION);
+ } finally {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
+}
+/**
+ * Returns the given file's contents as a character array.
+ */
+public static char[] getResourceContentsAsCharArray(IFile file) throws JavaModelException {
+ InputStream stream= null;
+ try {
+ stream = new BufferedInputStream(file.getContents(true));
+ } catch (CoreException e) {
+ throw new JavaModelException(e);
+ }
+ try {
+ return org.eclipse.jdt.internal.compiler.util.Util.getInputStreamAsCharArray(stream, -1);
+ } catch (IOException e) {
+ throw new JavaModelException(e, IJavaModelStatusConstants.IO_EXCEPTION);
+ } finally {
+ try {
+ stream.close();
+ } catch (IOException e) {
+ }
+ }
+}
/**
* Returns true if the given method signature is valid,
* false if it is not.
@@ -569,40 +616,6 @@ private static void quickSortReverse(String[] sortedCollection, int left, int ri
quickSortReverse(sortedCollection, left, original_right);
}
}
-public static byte[] readContentsAsBytes(InputStream input) throws IOException {
- BufferedInputStream bufferedInputStream = null;
- try {
- final int BUF_SIZE = 8192;
- byte[] buf = new byte[BUF_SIZE];
- int read;
- int totalRead = 0;
- bufferedInputStream = new BufferedInputStream(input);
- while (totalRead < BUF_SIZE && (read = bufferedInputStream.read(buf, totalRead, BUF_SIZE - totalRead)) != -1) {
- totalRead += read;
- }
- if (totalRead < BUF_SIZE) {
- byte[] result = new byte[totalRead];
- System.arraycopy(buf, 0, result, 0, totalRead);
- return result;
- }
- ByteArrayOutputStream out = new ByteArrayOutputStream(BUF_SIZE*2);
- out.write(buf);
- while ((read = bufferedInputStream.read(buf, 0, BUF_SIZE)) != -1) {
- out.write(buf, 0, read);
- }
- return out.toByteArray();
- }
- finally {
- try {
- if (bufferedInputStream != null) {
- bufferedInputStream.close();
- }
- }
- catch (IOException e) {
- // Ignore
- }
- }
-}
/**
* Sorts an array of objects in place, using the sort order given for each item.
*/
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/BuildNotifier.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/BuildNotifier.java
index 3c68416845..a782d8722b 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/BuildNotifier.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/BuildNotifier.java
@@ -157,10 +157,10 @@ protected String problemsMessage() {
return ""; //$NON-NLS-1$
}
if (numFixed == 0) {
- return '(' + numNew == 1 ? Util.bind("build.oneProblemFound", String.valueOf(numNew)) : Util.bind("build.problemsFound", String.valueOf(numNew)) +')'; //$NON-NLS-2$ //$NON-NLS-1$
+ return '(' + (numNew == 1 ? Util.bind("build.oneProblemFound", String.valueOf(numNew)) : Util.bind("build.problemsFound", String.valueOf(numNew))) +')'; //$NON-NLS-2$ //$NON-NLS-1$
} else
if (numNew == 0) {
- return '(' + numFixed == 1 ? Util.bind("build.oneProblemFixed", String.valueOf(numFixed)) : Util.bind("build.problemsFixed", String.valueOf(numFixed)) + ')'; //$NON-NLS-2$ //$NON-NLS-1$
+ return '(' + (numFixed == 1 ? Util.bind("build.oneProblemFixed", String.valueOf(numFixed)) : Util.bind("build.problemsFixed", String.valueOf(numFixed))) + ')'; //$NON-NLS-2$ //$NON-NLS-1$
} else {
return '(' + (numFixed == 1 ? Util.bind("build.oneProblemFixed", String.valueOf(numFixed)) : Util.bind("build.problemsFixed", String.valueOf(numFixed))) //$NON-NLS-2$ //$NON-NLS-1$
+ ", " //$NON-NLS-1$
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectBinaryOutput.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectBinaryOutput.java
index 6973b1669b..1253f661ed 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectBinaryOutput.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectBinaryOutput.java
@@ -15,9 +15,7 @@ import org.eclipse.jdt.internal.core.builder.IState;
import org.eclipse.jdt.internal.core.builder.IType;
import org.eclipse.jdt.internal.core.Util;
-import java.io.ByteArrayInputStream;
-import java.io.IOException;
-import java.io.InputStream;
+import java.io.*;
import java.util.*;
/**
@@ -136,12 +134,10 @@ public byte[] getBinary(TypeStructureEntry tsEntry, IType type) {
IPath path = getPathForBinary(type);
IFile file = getFile(path);
try {
- InputStream input = file.getContents(true);
- return Util.readContentsAsBytes(input);
- } catch (IOException e) {
- return new byte[0];
+ return Util.getResourceContentsAsByteArray(file);
} catch (CoreException e) {
- return new byte[0]; }
+ return new byte[0];
+ }
}
/**
* Returns the container for a path.
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectResourceCopier.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectResourceCopier.java
index 90194e8756..4182436cbe 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectResourceCopier.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/builder/impl/ProjectResourceCopier.java
@@ -210,8 +210,9 @@ private IPath getSourceFolderPath(IResource resource) {
IResource affectedResource = delta.getResource();
boolean processChildren = true;
switch (delta.getKind()) {
- case IResourceDelta.ADDED:
case IResourceDelta.CHANGED:
+ if ((delta.getFlags() & IResourceDelta.CONTENT) == 0) break; // only consider content change
+ case IResourceDelta.ADDED:
processChildren = copyToOutput(affectedResource);
break;
case IResourceDelta.REMOVED:
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/hierarchy/TypeHierarchy.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/hierarchy/TypeHierarchy.java
index afb64f0fd0..6095e7bd08 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/hierarchy/TypeHierarchy.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/hierarchy/TypeHierarchy.java
@@ -747,11 +747,26 @@ private boolean hasVisibilityChange(IJavaElementDelta delta) {
* the simple name of one of the types in this hierarchy.
*/
private boolean includesSupertypeOf(IType type) {
- IType[] supertypes = getSupertypes(type);
- for (int i = 0, length = supertypes.length; i < length; i++) {
- if (hasTypeNamed(supertypes[i].getElementName())) {
- return true;
+ try {
+ // check superclass
+ String superclassName = type.getSuperclassName();
+ if (superclassName != null) {
+ int lastSeparator = superclassName.lastIndexOf('.');
+ String simpleName = (lastSeparator > -1) ? superclassName.substring(lastSeparator) : superclassName;
+ if (hasTypeNamed(simpleName)) return true;
+ }
+
+ // check superinterfaces
+ String[] superinterfaceNames = type.getSuperInterfaceNames();
+ if (superinterfaceNames != null) {
+ for (int i = 0, length = superinterfaceNames.length; i < length; i++) {
+ String superinterfaceName = superinterfaceNames[i];
+ int lastSeparator = superinterfaceName.lastIndexOf('.');
+ String simpleName = (lastSeparator > -1) ? superinterfaceName.substring(lastSeparator) : superinterfaceName;
+ if (hasTypeNamed(simpleName)) return true;
+ }
}
+ } catch (JavaModelException e) {
}
return false;
}
diff --git a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/jdom/SimpleDOMBuilder.java b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/jdom/SimpleDOMBuilder.java
index 214c053afe..04f409b625 100644
--- a/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/jdom/SimpleDOMBuilder.java
+++ b/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/jdom/SimpleDOMBuilder.java
@@ -33,14 +33,6 @@ public void acceptImport(int declarationStart, int declarationEnd, char[] name,
addChild(fNode);
}
/**
-
- */
-public void acceptInitializer(int modifiers, int declarationSourceStart, int declarationSourceEnd) {
- int[] sourceRange = {declarationSourceStart, declarationSourceEnd};
- fNode = new DOMInitializer(fDocument, sourceRange, modifiers);
- addChild(fNode);
-}
-/**
*/
public void acceptPackage(int declarationStart, int declarationEnd, char[] name) {
int[] sourceRange= new int[] {declarationStart, declarationEnd};
@@ -124,6 +116,15 @@ public void enterField(int declarationStart, int modifiers, char[] type, char[]
fStack.push(fNode);
}
/**
+
+ */
+public void enterInitializer(int declarationSourceStart, int modifiers) {
+ int[] sourceRange = {declarationSourceStart, -1};
+ fNode = new DOMInitializer(fDocument, sourceRange, modifiers);
+ addChild(fNode);
+ fStack.push(fNode);
+}
+/**
*/
public void enterInterface(int declarationStart, int modifiers, char[] name, int nameStart, int nameEnd, char[][] superinterfaces) {
enterType(declarationStart, modifiers, name, nameStart, nameEnd, null,
@@ -174,6 +175,11 @@ public void exitField(int declarationEnd) {
}
/**
*/
+public void exitInitializer(int declarationEnd) {
+ exitMember(declarationEnd);
+}
+/**
+ */
public void exitInterface(int declarationEnd) {
exitType(declarationEnd);
}
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/core/search/SearchEngine.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/core/search/SearchEngine.java
index b3d61db06c..4b0daf6108 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/core/search/SearchEngine.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/core/search/SearchEngine.java
@@ -367,10 +367,14 @@ public void searchAllTypeNames(
IIndexSearchRequestor searchRequestor = new IndexSearchAdapter(){
public void acceptClassDeclaration(String resourcePath, char[] simpleTypeName, char[][] enclosingTypeNames, char[] packageName) {
- nameRequestor.acceptClass(packageName, simpleTypeName, enclosingTypeNames, resourcePath);
+ if (enclosingTypeNames != IIndexConstants.ONE_ZERO_CHAR) { // filter out local and anonymous classes
+ nameRequestor.acceptClass(packageName, simpleTypeName, enclosingTypeNames, resourcePath);
+ }
}
public void acceptInterfaceDeclaration(String resourcePath, char[] simpleTypeName, char[][] enclosingTypeNames, char[] packageName) {
- nameRequestor.acceptInterface(packageName, simpleTypeName, enclosingTypeNames, resourcePath);
+ if (enclosingTypeNames != IIndexConstants.ONE_ZERO_CHAR) { // filter out local and anonymous classes
+ nameRequestor.acceptInterface(packageName, simpleTypeName, enclosingTypeNames, resourcePath);
+ }
}
};
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/FileDocument.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/FileDocument.java
index b6d03a05f1..769bdcd631 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/FileDocument.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/FileDocument.java
@@ -22,13 +22,13 @@ public class FileDocument extends PropertyDocument {
* @see IDocument#getByteContent
*/
public byte[] getByteContent() throws IOException {
- return Util.getFileByteContent(file);
+ return org.eclipse.jdt.internal.compiler.util.Util.getFileByteContent(file);
}
/**
* @see IDocument#getCharContent
*/
public char[] getCharContent() throws IOException {
- return Util.getFileCharContent(file);
+ return org.eclipse.jdt.internal.compiler.util.Util.getFileCharContent(file);
}
/**
* @see IDocument#getName
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/IFileDocument.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/IFileDocument.java
index c6fb8149ae..5f37124a6c 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/IFileDocument.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/index/impl/IFileDocument.java
@@ -46,7 +46,7 @@ public class IFileDocument extends PropertyDocument {
if (byteContents != null) return byteContents;
IPath location = file.getLocation();
if (location == null) return new byte[0];
- return byteContents = Util.getFileByteContent(location.toFile());
+ return byteContents = org.eclipse.jdt.internal.compiler.util.Util.getFileByteContent(location.toFile());
}
/**
* @see IDocument#getCharContent
@@ -55,7 +55,7 @@ public class IFileDocument extends PropertyDocument {
if (charContents != null) return charContents;
IPath location = file.getLocation();
if (location == null) return new char[0];
- return charContents = Util.getFileCharContent(location.toFile());
+ return charContents = org.eclipse.jdt.internal.compiler.util.Util.getFileCharContent(location.toFile());
}
/**
* @see IDocument#getName
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddClassFileToIndex.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddClassFileToIndex.java
index 4d59493a9b..a97a56678f 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddClassFileToIndex.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddClassFileToIndex.java
@@ -61,7 +61,7 @@ public void initializeContents() {
try {
IPath location = resource.getLocation();
if (location != null){;
- this.contents = Util.getFileByteContent(resource.getLocation().toFile());
+ this.contents = org.eclipse.jdt.internal.compiler.util.Util.getFileByteContent(resource.getLocation().toFile());
}
} catch (IOException e) {
}
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddCompilationUnitToIndex.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddCompilationUnitToIndex.java
index 9b3968e1be..490fa19f88 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddCompilationUnitToIndex.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddCompilationUnitToIndex.java
@@ -62,7 +62,7 @@ public void initializeContents() {
try {
IPath location = resource.getLocation();
if (location != null){
- this.contents = Util.getFileCharContent(location.toFile());
+ this.contents = org.eclipse.jdt.internal.compiler.util.Util.getFileCharContent(location.toFile());
}
} catch (IOException e) {
}
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddJarFileToIndex.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddJarFileToIndex.java
index b922727254..2b24a5e4fb 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddJarFileToIndex.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/AddJarFileToIndex.java
@@ -117,16 +117,7 @@ public boolean execute() {
// iterate each entry to index it
ZipEntry ze = (ZipEntry) e.nextElement();
if (Util.isClassFileName(ze.getName())) {
- InputStream zipInputStream = zip.getInputStream(ze);
- byte classFileBytes[] = new byte[(int) ze.getSize()];
- int length = classFileBytes.length;
- int len = 0;
- int readSize = 0;
- while ((readSize != -1) && (len != length)) {
- readSize = zipInputStream.read(classFileBytes, len, length - len);
- len += readSize;
- }
- zipInputStream.close();
+ byte[] classFileBytes = org.eclipse.jdt.internal.compiler.util.Util.getZipEntryByteContent(ze, zip);
// Add the name of the file to the index
index.add(
new JarFileEntryDocument(ze, classFileBytes, zipFilePath),
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/IIndexConstants.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/IIndexConstants.java
index b15a260b44..4e6c6b18f3 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/IIndexConstants.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/IIndexConstants.java
@@ -34,4 +34,8 @@ public interface IIndexConstants extends IJobConstants {
char[] ONE_STAR = new char[] {'*'};
char[] NO_CHAR = new char[0];
char[][] NO_CHAR_CHAR = new char[0][];
+
+ // used as special marker for enclosing type name of local and anonymous classes
+ char[] ONE_ZERO = new char[] {'0'};
+ char[][] ONE_ZERO_CHAR = new char[][] {ONE_ZERO};
}
diff --git a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/SourceIndexer.java b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/SourceIndexer.java
index f2b3553f49..4925171357 100644
--- a/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/SourceIndexer.java
+++ b/org.eclipse.jdt.core/search/org/eclipse/jdt/internal/core/search/indexing/SourceIndexer.java
@@ -48,7 +48,7 @@ protected void indexFile(IDocument document) throws IOException {
// Create a new Parser
SourceIndexerRequestor requestor = new SourceIndexerRequestor(this, document);
- SourceElementParser parser = new SourceElementParser(requestor, problemFactory);
+ SourceElementParser parser = new SourceElementParser(requestor, problemFactory, true); // index local declarations
// Launch the parser
char[] source = null;

Back to the top