View | Details | Raw Unified | Return to bug 171184
Collapse All | Expand All

(-)eval/org/eclipse/jdt/internal/eval/CodeSnippetTypeDeclaration.java (-12 / +9 lines)
Lines 39-59 Link Here
39
		ClassFile classFile = new CodeSnippetClassFile(this.binding, enclosingClassFile, false);
39
		ClassFile classFile = new CodeSnippetClassFile(this.binding, enclosingClassFile, false);
40
		// generate all fiels
40
		// generate all fiels
41
		classFile.addFieldInfos();
41
		classFile.addFieldInfos();
42
42
		if (this.binding.isMemberType()) {
43
		// record the inner type inside its own .class file to be able
43
			classFile.recordInnerClasses(this.binding);
44
		// to generate inner classes attributes
44
		} else if (this.binding.isLocalType()) {
45
		if (this.binding.isMemberType())
45
			enclosingClassFile.recordInnerClasses(this.binding);
46
			classFile.recordEnclosingTypeAttributes(this.binding);
46
			classFile.recordInnerClasses(this.binding);
47
		if (this.binding.isLocalType()) {
48
			enclosingClassFile.recordNestedLocalAttribute(this.binding);
49
			classFile.recordNestedLocalAttribute(this.binding);
50
		}
47
		}
48
51
		if (this.memberTypes != null) {
49
		if (this.memberTypes != null) {
52
			for (int i = 0, max = this.memberTypes.length; i < max; i++) {
50
			for (int i = 0, max = this.memberTypes.length; i < max; i++) {
53
				// record the inner type inside its own .class file to be able
51
				TypeDeclaration memberType = this.memberTypes[i];
54
				// to generate inner classes attributes
52
				classFile.recordInnerClasses(memberType.binding);
55
				classFile.recordNestedMemberAttribute(this.memberTypes[i].binding);
53
				memberType.generateCode(this.scope, classFile);
56
				this.memberTypes[i].generateCode(this.scope, classFile);
57
			}
54
			}
58
		}
55
		}
59
		// generate all methods
56
		// generate all methods
(-)eval/org/eclipse/jdt/internal/eval/CodeSnippetClassFile.java (-7 / +6 lines)
Lines 88-94 Link Here
88
	// now we continue to generate the bytes inside the contents array
88
	// now we continue to generate the bytes inside the contents array
89
	this.contents[this.contentsOffset++] = (byte) (accessFlags >> 8);
89
	this.contents[this.contentsOffset++] = (byte) (accessFlags >> 8);
90
	this.contents[this.contentsOffset++] = (byte) accessFlags;
90
	this.contents[this.contentsOffset++] = (byte) accessFlags;
91
	int classNameIndex = this.constantPool.literalIndexForType(aType.constantPoolName());
91
	int classNameIndex = this.constantPool.literalIndexForType(aType);
92
	this.contents[this.contentsOffset++] = (byte) (classNameIndex >> 8);
92
	this.contents[this.contentsOffset++] = (byte) (classNameIndex >> 8);
93
	this.contents[this.contentsOffset++] = (byte) classNameIndex;
93
	this.contents[this.contentsOffset++] = (byte) classNameIndex;
94
	int superclassNameIndex;
94
	int superclassNameIndex;
Lines 96-102 Link Here
96
		superclassNameIndex = this.constantPool.literalIndexForType(ConstantPool.JavaLangObjectConstantPoolName);
96
		superclassNameIndex = this.constantPool.literalIndexForType(ConstantPool.JavaLangObjectConstantPoolName);
97
	} else {
97
	} else {
98
		superclassNameIndex =
98
		superclassNameIndex =
99
			(aType.superclass == null ? 0 : this.constantPool.literalIndexForType(aType.superclass.constantPoolName()));
99
			(aType.superclass == null ? 0 : this.constantPool.literalIndexForType(aType.superclass));
100
	}
100
	}
101
	this.contents[this.contentsOffset++] = (byte) (superclassNameIndex >> 8);
101
	this.contents[this.contentsOffset++] = (byte) (superclassNameIndex >> 8);
102
	this.contents[this.contentsOffset++] = (byte) superclassNameIndex;
102
	this.contents[this.contentsOffset++] = (byte) superclassNameIndex;
Lines 106-118 Link Here
106
	this.contents[this.contentsOffset++] = (byte) interfacesCount;
106
	this.contents[this.contentsOffset++] = (byte) interfacesCount;
107
	if (superInterfacesBinding != null) {
107
	if (superInterfacesBinding != null) {
108
		for (int i = 0; i < interfacesCount; i++) {
108
		for (int i = 0; i < interfacesCount; i++) {
109
			int interfaceIndex = this.constantPool.literalIndexForType(superInterfacesBinding[i].constantPoolName());
109
			int interfaceIndex = this.constantPool.literalIndexForType(superInterfacesBinding[i]);
110
			this.contents[this.contentsOffset++] = (byte) (interfaceIndex >> 8);
110
			this.contents[this.contentsOffset++] = (byte) (interfaceIndex >> 8);
111
			this.contents[this.contentsOffset++] = (byte) interfaceIndex;
111
			this.contents[this.contentsOffset++] = (byte) interfaceIndex;
112
		}
112
		}
113
	}
113
	}
114
	this.produceAttributes = this.referenceBinding.scope.compilerOptions().produceDebugAttributes;
114
	this.produceAttributes = this.referenceBinding.scope.compilerOptions().produceDebugAttributes;
115
	this.innerClassesBindings = new ReferenceBinding[INNER_CLASSES_SIZE];
116
	this.creatingProblemType = creatingProblemType;
115
	this.creatingProblemType = creatingProblemType;
117
	if (this.targetJDK >= ClassFileConstants.JDK1_6) {
116
	if (this.targetJDK >= ClassFileConstants.JDK1_6) {
118
		this.codeStream = new StackMapFrameCodeStream(this);
117
		this.codeStream = new StackMapFrameCodeStream(this);
Lines 141-148 Link Here
141
	ClassFile classFile = new CodeSnippetClassFile(typeBinding, null, true);
140
	ClassFile classFile = new CodeSnippetClassFile(typeBinding, null, true);
142
141
143
	// inner attributes
142
	// inner attributes
144
	if (typeBinding.isMemberType())
143
	if (typeBinding.isNestedType()) {
145
		classFile.recordEnclosingTypeAttributes(typeBinding);
144
		classFile.recordInnerClasses(typeBinding);
145
	}
146
146
147
	// add its fields
147
	// add its fields
148
	FieldBinding[] fields = typeBinding.fields();
148
	FieldBinding[] fields = typeBinding.fields();
Lines 195-201 Link Here
195
		for (int i = 0, max = typeDeclaration.memberTypes.length; i < max; i++) {
195
		for (int i = 0, max = typeDeclaration.memberTypes.length; i < max; i++) {
196
			TypeDeclaration memberType = typeDeclaration.memberTypes[i];
196
			TypeDeclaration memberType = typeDeclaration.memberTypes[i];
197
			if (memberType.binding != null) {
197
			if (memberType.binding != null) {
198
				classFile.recordNestedMemberAttribute(memberType.binding);
199
				ClassFile.createProblemType(memberType, unitResult);
198
				ClassFile.createProblemType(memberType, unitResult);
200
			}
199
			}
201
		}
200
		}
(-)compiler/org/eclipse/jdt/internal/compiler/lookup/TagBits.java (+1 lines)
Lines 31-36 Link Here
31
	// for the type cycle hierarchy check used by ClassScope
31
	// for the type cycle hierarchy check used by ClassScope
32
	long BeginHierarchyCheck = ASTNode.Bit9;  // type
32
	long BeginHierarchyCheck = ASTNode.Bit9;  // type
33
	long EndHierarchyCheck = ASTNode.Bit10; // type
33
	long EndHierarchyCheck = ASTNode.Bit10; // type
34
	long ContainsNestedTypesInSignature = ASTNode.Bit10; // method
34
	long HasParameterAnnotations = ASTNode.Bit11; // method
35
	long HasParameterAnnotations = ASTNode.Bit11; // method
35
	
36
	
36
	// test bit to see if default abstract methods were computed
37
	// test bit to see if default abstract methods were computed
(-)compiler/org/eclipse/jdt/internal/compiler/lookup/MethodBinding.java (+136 lines)
Lines 11-16 Link Here
11
package org.eclipse.jdt.internal.compiler.lookup;
11
package org.eclipse.jdt.internal.compiler.lookup;
12
12
13
import org.eclipse.jdt.core.compiler.CharOperation;
13
import org.eclipse.jdt.core.compiler.CharOperation;
14
import org.eclipse.jdt.internal.compiler.ClassFile;
14
import org.eclipse.jdt.internal.compiler.ast.ASTNode;
15
import org.eclipse.jdt.internal.compiler.ast.ASTNode;
15
import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
16
import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
16
import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
17
import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
Lines 771-776 Link Here
771
	
772
	
772
	return signature;
773
	return signature;
773
}
774
}
775
/*
776
 * This method is used to record references to nested types inside the method signature.
777
 * This is the one that must be used during code generation.
778
 * 
779
 * See https://bugs.eclipse.org/bugs/show_bug.cgi?id=171184
780
 */
781
public final char[] signature(ClassFile classFile) {
782
	if (signature != null) {
783
		if ((this.tagBits & TagBits.ContainsNestedTypesInSignature) != 0) { 
784
			// we need to record inner classes references
785
			boolean isConstructor = isConstructor();
786
			TypeBinding[] targetParameters = this.parameters;
787
			boolean needSynthetics = isConstructor && declaringClass.isNestedType();
788
			if (needSynthetics) {
789
				// take into account the synthetic argument type signatures as well
790
				ReferenceBinding[] syntheticArgumentTypes = declaringClass.syntheticEnclosingInstanceTypes();
791
				if (syntheticArgumentTypes != null) {
792
					for (int i = 0, count = syntheticArgumentTypes.length; i < count; i++) {
793
						ReferenceBinding syntheticArgumentType = syntheticArgumentTypes[i];
794
						if (syntheticArgumentType.isNestedType()) {
795
							this.tagBits |= TagBits.ContainsNestedTypesInSignature;
796
							classFile.recordInnerClasses(syntheticArgumentType);
797
						}
798
					}
799
				}
800
				
801
				if (this instanceof SyntheticMethodBinding) {
802
					targetParameters = ((SyntheticMethodBinding)this).targetMethod.parameters;
803
				}
804
			}
805
806
			if (targetParameters != Binding.NO_PARAMETERS) {
807
				for (int i = 0; i < targetParameters.length; i++) {
808
					TypeBinding targetParameter = targetParameters[i];
809
					TypeBinding leafTargetParameterType = targetParameter.leafComponentType();
810
					if (leafTargetParameterType.isNestedType()) {
811
						this.tagBits |= TagBits.ContainsNestedTypesInSignature;
812
						classFile.recordInnerClasses(leafTargetParameterType);
813
					}
814
				}
815
			}
816
			if (needSynthetics) {
817
				// move the extra padding arguments of the synthetic constructor invocation to the end		
818
				for (int i = targetParameters.length, extraLength = parameters.length; i < extraLength; i++) {
819
					TypeBinding parameter = parameters[i];
820
					TypeBinding leafParameterType = parameter.leafComponentType();
821
					if (leafParameterType.isNestedType()) {
822
						this.tagBits |= TagBits.ContainsNestedTypesInSignature;
823
						classFile.recordInnerClasses(leafParameterType);
824
					}
825
				}
826
			}
827
			if (this.returnType != null) {
828
				TypeBinding ret = this.returnType.leafComponentType();
829
				if (ret.isNestedType()) {
830
					this.tagBits |= TagBits.ContainsNestedTypesInSignature;
831
					classFile.recordInnerClasses(ret);
832
				}
833
			}
834
		}
835
		return signature;
836
	}
837
838
	StringBuffer buffer = new StringBuffer(parameters.length + 1 * 20);
839
	buffer.append('(');
840
	
841
	TypeBinding[] targetParameters = this.parameters;
842
	boolean isConstructor = isConstructor();
843
	if (isConstructor && declaringClass.isEnum()) { // insert String name,int ordinal 
844
		buffer.append(ConstantPool.JavaLangStringSignature);
845
		buffer.append(TypeBinding.INT.signature());
846
	}
847
	boolean needSynthetics = isConstructor && declaringClass.isNestedType();
848
	if (needSynthetics) {
849
		// take into account the synthetic argument type signatures as well
850
		ReferenceBinding[] syntheticArgumentTypes = declaringClass.syntheticEnclosingInstanceTypes();
851
		if (syntheticArgumentTypes != null) {
852
			for (int i = 0, count = syntheticArgumentTypes.length; i < count; i++) {
853
				ReferenceBinding syntheticArgumentType = syntheticArgumentTypes[i];
854
				if (syntheticArgumentType.isNestedType()) {
855
					this.tagBits |= TagBits.ContainsNestedTypesInSignature;
856
					classFile.recordInnerClasses(syntheticArgumentType);
857
				}
858
				buffer.append(syntheticArgumentType.signature());
859
			}
860
		}
861
		
862
		if (this instanceof SyntheticMethodBinding) {
863
			targetParameters = ((SyntheticMethodBinding)this).targetMethod.parameters;
864
		}
865
	}
866
867
	if (targetParameters != Binding.NO_PARAMETERS) {
868
		for (int i = 0; i < targetParameters.length; i++) {
869
			TypeBinding targetParameter = targetParameters[i];
870
			TypeBinding leafTargetParameterType = targetParameter.leafComponentType();
871
			if (leafTargetParameterType.isNestedType()) {
872
				this.tagBits |= TagBits.ContainsNestedTypesInSignature;
873
				classFile.recordInnerClasses(leafTargetParameterType);
874
			}
875
			buffer.append(targetParameter.signature());
876
		}
877
	}
878
	if (needSynthetics) {
879
		SyntheticArgumentBinding[] syntheticOuterArguments = declaringClass.syntheticOuterLocalVariables();
880
		int count = syntheticOuterArguments == null ? 0 : syntheticOuterArguments.length;
881
		for (int i = 0; i < count; i++) {
882
			buffer.append(syntheticOuterArguments[i].type.signature());
883
		}
884
		// move the extra padding arguments of the synthetic constructor invocation to the end		
885
		for (int i = targetParameters.length, extraLength = parameters.length; i < extraLength; i++) {
886
			TypeBinding parameter = parameters[i];
887
			TypeBinding leafParameterType = parameter.leafComponentType();
888
			if (leafParameterType.isNestedType()) {
889
				this.tagBits |= TagBits.ContainsNestedTypesInSignature;
890
				classFile.recordInnerClasses(leafParameterType);
891
			}
892
			buffer.append(parameter.signature());
893
		}
894
	}
895
	buffer.append(')');
896
	if (this.returnType != null) {
897
		TypeBinding ret = this.returnType.leafComponentType();
898
		if (ret.isNestedType()) {
899
			this.tagBits |= TagBits.ContainsNestedTypesInSignature;
900
			classFile.recordInnerClasses(ret);
901
		}
902
		buffer.append(this.returnType.signature());
903
	}
904
	int nameLength = buffer.length();
905
	signature = new char[nameLength];
906
	buffer.getChars(0, nameLength, signature, 0);	    
907
	
908
	return signature;
909
}
774
public final int sourceEnd() {
910
public final int sourceEnd() {
775
	AbstractMethodDeclaration method = sourceMethod();
911
	AbstractMethodDeclaration method = sourceMethod();
776
	if (method == null) {
912
	if (method == null) {
(-)compiler/org/eclipse/jdt/internal/compiler/ast/TypeDeclaration.java (-12 / +10 lines)
Lines 504-526 Link Here
504
		// create the result for a compiled type
504
		// create the result for a compiled type
505
		ClassFile classFile = ClassFile.getNewInstance(this.binding);
505
		ClassFile classFile = ClassFile.getNewInstance(this.binding);
506
		classFile.initialize(this.binding, enclosingClassFile, false);
506
		classFile.initialize(this.binding, enclosingClassFile, false);
507
		if (this.binding.isMemberType()) {
508
			classFile.recordInnerClasses(this.binding);
509
		} else if (this.binding.isLocalType()) {
510
			enclosingClassFile.recordInnerClasses(this.binding);
511
			classFile.recordInnerClasses(this.binding);
512
		}
513
507
		// generate all fiels
514
		// generate all fiels
508
		classFile.addFieldInfos();
515
		classFile.addFieldInfos();
509
516
510
		// record the inner type inside its own .class file to be able
511
		// to generate inner classes attributes
512
		if (this.binding.isMemberType())
513
			classFile.recordEnclosingTypeAttributes(this.binding);
514
		if (this.binding.isLocalType()) {
515
			enclosingClassFile.recordNestedLocalAttribute(this.binding);
516
			classFile.recordNestedLocalAttribute(this.binding);
517
		}
518
		if (this.memberTypes != null) {
517
		if (this.memberTypes != null) {
519
			for (int i = 0, max = this.memberTypes.length; i < max; i++) {
518
			for (int i = 0, max = this.memberTypes.length; i < max; i++) {
520
				// record the inner type inside its own .class file to be able
519
				TypeDeclaration memberType = this.memberTypes[i];
521
				// to generate inner classes attributes
520
				classFile.recordInnerClasses(memberType.binding);
522
				classFile.recordNestedMemberAttribute(this.memberTypes[i].binding);
521
				memberType.generateCode(this.scope, classFile);
523
				this.memberTypes[i].generateCode(this.scope, classFile);
524
			}
522
			}
525
		}
523
		}
526
		// generate all methods
524
		// generate all methods
(-)compiler/org/eclipse/jdt/internal/compiler/ast/AbstractMethodDeclaration.java (-1 / +1 lines)
Lines 73-79 Link Here
73
73
74
	public abstract void analyseCode(ClassScope classScope, InitializationFlowContext initializationContext, FlowInfo info);
74
	public abstract void analyseCode(ClassScope classScope, InitializationFlowContext initializationContext, FlowInfo info);
75
75
76
		/**
76
	/**
77
	 * Bind and add argument's binding into the scope of the method
77
	 * Bind and add argument's binding into the scope of the method
78
	 */
78
	 */
79
	public void bindArguments() {
79
	public void bindArguments() {
(-)compiler/org/eclipse/jdt/internal/compiler/ClassFile.java (-170 / +100 lines)
Lines 15-21 Link Here
15
import java.io.FileOutputStream;
15
import java.io.FileOutputStream;
16
import java.io.IOException;
16
import java.io.IOException;
17
import java.util.ArrayList;
17
import java.util.ArrayList;
18
import java.util.Arrays;
18
import java.util.Collections;
19
import java.util.Collections;
20
import java.util.Comparator;
21
import java.util.HashSet;
19
import java.util.Set;
22
import java.util.Set;
20
import java.util.StringTokenizer;
23
import java.util.StringTokenizer;
21
24
Lines 106-115 Link Here
106
	public byte[] header;
109
	public byte[] header;
107
	// that collection contains all the remaining bytes of the .class file
110
	// that collection contains all the remaining bytes of the .class file
108
	public int headerOffset;
111
	public int headerOffset;
109
	public ReferenceBinding[] innerClassesBindings;
112
	public Set innerClassesBindings;
110
	public int methodCount;
113
	public int methodCount;
111
	public int methodCountOffset;
114
	public int methodCountOffset;
112
	public int numberOfInnerClasses;
113
	// pool managment
115
	// pool managment
114
	public boolean isShared = false;
116
	public boolean isShared = false;
115
	// used to generate private access methods
117
	// used to generate private access methods
Lines 256-264 Link Here
256
		// TODO (olivier) handle cases where a field cannot be generated (name too long)
258
		// TODO (olivier) handle cases where a field cannot be generated (name too long)
257
		// TODO (olivier) handle too many methods
259
		// TODO (olivier) handle too many methods
258
		// inner attributes
260
		// inner attributes
259
		if (typeBinding.isMemberType())
261
		if (typeBinding.isNestedType()) {
260
			classFile.recordEnclosingTypeAttributes(typeBinding);
262
			classFile.recordInnerClasses(typeBinding);
261
	
263
		}
264
262
		// add its fields
265
		// add its fields
263
		FieldBinding[] fields = typeBinding.fields();
266
		FieldBinding[] fields = typeBinding.fields();
264
		if ((fields != null) && (fields != Binding.NO_FIELDS)) {
267
		if ((fields != null) && (fields != Binding.NO_FIELDS)) {
Lines 312-318 Link Here
312
			for (int i = 0, max = typeDeclaration.memberTypes.length; i < max; i++) {
315
			for (int i = 0, max = typeDeclaration.memberTypes.length; i < max; i++) {
313
				TypeDeclaration memberType = typeDeclaration.memberTypes[i];
316
				TypeDeclaration memberType = typeDeclaration.memberTypes[i];
314
				if (memberType.binding != null) {
317
				if (memberType.binding != null) {
315
					classFile.recordNestedMemberAttribute(memberType.binding);
316
					ClassFile.createProblemType(memberType, unitResult);
318
					ClassFile.createProblemType(memberType, unitResult);
317
				}
319
				}
318
			}
320
			}
Lines 496-560 Link Here
496
			contents[contentsOffset++] = 0;
498
			contents[contentsOffset++] = 0;
497
			attributeNumber++;
499
			attributeNumber++;
498
		}
500
		}
499
		// Inner class attribute
500
		if (numberOfInnerClasses != 0) {
501
			// Generate the inner class attribute
502
			int exSize = 8 * numberOfInnerClasses + 8;
503
			if (exSize + contentsOffset >= this.contents.length) {
504
				resizeContents(exSize);
505
			}
506
			// Now we now the size of the attribute and the number of entries
507
			// attribute name
508
			int attributeNameIndex =
509
				constantPool.literalIndex(AttributeNamesConstants.InnerClassName);
510
			contents[contentsOffset++] = (byte) (attributeNameIndex >> 8);
511
			contents[contentsOffset++] = (byte) attributeNameIndex;
512
			int value = (numberOfInnerClasses << 3) + 2;
513
			contents[contentsOffset++] = (byte) (value >> 24);
514
			contents[contentsOffset++] = (byte) (value >> 16);
515
			contents[contentsOffset++] = (byte) (value >> 8);
516
			contents[contentsOffset++] = (byte) value;
517
			contents[contentsOffset++] = (byte) (numberOfInnerClasses >> 8);
518
			contents[contentsOffset++] = (byte) numberOfInnerClasses;
519
			for (int i = 0; i < numberOfInnerClasses; i++) {
520
				ReferenceBinding innerClass = innerClassesBindings[i];
521
				int accessFlags = innerClass.getAccessFlags();
522
				int innerClassIndex = constantPool.literalIndexForType(innerClass.constantPoolName());
523
				// inner class index
524
				contents[contentsOffset++] = (byte) (innerClassIndex >> 8);
525
				contents[contentsOffset++] = (byte) innerClassIndex;
526
				// outer class index: anonymous and local have no outer class index
527
				if (innerClass.isMemberType()) {
528
					// member or member of local
529
					int outerClassIndex = constantPool.literalIndexForType(innerClass.enclosingType().constantPoolName());
530
					contents[contentsOffset++] = (byte) (outerClassIndex >> 8);
531
					contents[contentsOffset++] = (byte) outerClassIndex;
532
				} else {
533
					// equals to 0 if the innerClass is not a member type
534
					contents[contentsOffset++] = 0;
535
					contents[contentsOffset++] = 0;
536
				}
537
				// name index
538
				if (!innerClass.isAnonymousType()) {
539
					int nameIndex = constantPool.literalIndex(innerClass.sourceName());
540
					contents[contentsOffset++] = (byte) (nameIndex >> 8);
541
					contents[contentsOffset++] = (byte) nameIndex;
542
				} else {
543
					// equals to 0 if the innerClass is an anonymous type
544
					contents[contentsOffset++] = 0;
545
					contents[contentsOffset++] = 0;
546
				}
547
				// access flag
548
				if (innerClass.isAnonymousType()) {
549
					accessFlags &= ~ClassFileConstants.AccFinal;
550
				} else if (innerClass.isMemberType() && innerClass.isInterface()) {
551
					accessFlags |= ClassFileConstants.AccStatic; // implicitely static
552
				}
553
				contents[contentsOffset++] = (byte) (accessFlags >> 8);
554
				contents[contentsOffset++] = (byte) accessFlags;
555
			}
556
			attributeNumber++;
557
		}
558
		// add signature attribute
501
		// add signature attribute
559
		char[] genericSignature = referenceBinding.genericSignature();
502
		char[] genericSignature = referenceBinding.genericSignature();
560
		if (genericSignature != null) {
503
		if (genericSignature != null) {
Lines 603-609 Link Here
603
			if (this.referenceBinding instanceof LocalTypeBinding) {
546
			if (this.referenceBinding instanceof LocalTypeBinding) {
604
				MethodBinding methodBinding = ((LocalTypeBinding) this.referenceBinding).enclosingMethod;
547
				MethodBinding methodBinding = ((LocalTypeBinding) this.referenceBinding).enclosingMethod;
605
				if (methodBinding != null) {
548
				if (methodBinding != null) {
606
					int enclosingMethodIndex = constantPool.literalIndexForNameAndType(methodBinding.selector, methodBinding.signature());
549
					int enclosingMethodIndex = constantPool.literalIndexForNameAndType(methodBinding.selector, methodBinding.signature(this));
607
					methodIndexByte1 = (byte) (enclosingMethodIndex >> 8);
550
					methodIndexByte1 = (byte) (enclosingMethodIndex >> 8);
608
					methodIndexByte2 = (byte) enclosingMethodIndex;
551
					methodIndexByte2 = (byte) enclosingMethodIndex;
609
				}
552
				}
Lines 638-643 Link Here
638
			contents[contentsOffset++] = 0;
581
			contents[contentsOffset++] = 0;
639
			attributeNumber++;
582
			attributeNumber++;
640
		}
583
		}
584
		// Inner class attribute
585
		int numberOfInnerClasses = this.innerClassesBindings == null ? 0 : this.innerClassesBindings.size();
586
		if (numberOfInnerClasses != 0) {
587
			ReferenceBinding[] innerClasses = new ReferenceBinding[numberOfInnerClasses];
588
			this.innerClassesBindings.toArray(innerClasses);
589
			Arrays.sort(innerClasses, new Comparator() {
590
				public int compare(Object o1, Object o2) {
591
					TypeBinding binding1 = (TypeBinding) o1;
592
					TypeBinding binding2 = (TypeBinding) o2;
593
					return CharOperation.compareTo(binding1.constantPoolName(), binding2.constantPoolName());
594
				}
595
			});
596
			// Generate the inner class attribute
597
			int exSize = 8 * numberOfInnerClasses + 8;
598
			if (exSize + contentsOffset >= this.contents.length) {
599
				resizeContents(exSize);
600
			}
601
			// Now we now the size of the attribute and the number of entries
602
			// attribute name
603
			int attributeNameIndex =
604
				constantPool.literalIndex(AttributeNamesConstants.InnerClassName);
605
			contents[contentsOffset++] = (byte) (attributeNameIndex >> 8);
606
			contents[contentsOffset++] = (byte) attributeNameIndex;
607
			int value = (numberOfInnerClasses << 3) + 2;
608
			contents[contentsOffset++] = (byte) (value >> 24);
609
			contents[contentsOffset++] = (byte) (value >> 16);
610
			contents[contentsOffset++] = (byte) (value >> 8);
611
			contents[contentsOffset++] = (byte) value;
612
			contents[contentsOffset++] = (byte) (numberOfInnerClasses >> 8);
613
			contents[contentsOffset++] = (byte) numberOfInnerClasses;
614
			for (int i = 0; i < numberOfInnerClasses; i++) {
615
				ReferenceBinding innerClass = innerClasses[i];
616
				int accessFlags = innerClass.getAccessFlags();
617
				int innerClassIndex = constantPool.literalIndexForType(innerClass.constantPoolName());
618
				// inner class index
619
				contents[contentsOffset++] = (byte) (innerClassIndex >> 8);
620
				contents[contentsOffset++] = (byte) innerClassIndex;
621
				// outer class index: anonymous and local have no outer class index
622
				if (innerClass.isMemberType()) {
623
					// member or member of local
624
					int outerClassIndex = constantPool.literalIndexForType(innerClass.enclosingType().constantPoolName());
625
					contents[contentsOffset++] = (byte) (outerClassIndex >> 8);
626
					contents[contentsOffset++] = (byte) outerClassIndex;
627
				} else {
628
					// equals to 0 if the innerClass is not a member type
629
					contents[contentsOffset++] = 0;
630
					contents[contentsOffset++] = 0;
631
				}
632
				// name index
633
				if (!innerClass.isAnonymousType()) {
634
					int nameIndex = constantPool.literalIndex(innerClass.sourceName());
635
					contents[contentsOffset++] = (byte) (nameIndex >> 8);
636
					contents[contentsOffset++] = (byte) nameIndex;
637
				} else {
638
					// equals to 0 if the innerClass is an anonymous type
639
					contents[contentsOffset++] = 0;
640
					contents[contentsOffset++] = 0;
641
				}
642
				// access flag
643
				if (innerClass.isAnonymousType()) {
644
					accessFlags &= ~ClassFileConstants.AccFinal;
645
				} else if (innerClass.isMemberType() && innerClass.isInterface()) {
646
					accessFlags |= ClassFileConstants.AccStatic; // implicitely static
647
				}
648
				contents[contentsOffset++] = (byte) (accessFlags >> 8);
649
				contents[contentsOffset++] = (byte) accessFlags;
650
			}
651
			attributeNumber++;
652
		}
641
		// update the number of attributes
653
		// update the number of attributes
642
		if (attributeOffset + 2 >= this.contents.length) {
654
		if (attributeOffset + 2 >= this.contents.length) {
643
			resizeContents(2);
655
			resizeContents(2);
Lines 840-846 Link Here
840
		contents[contentsOffset++] = (byte) (nameIndex >> 8);
852
		contents[contentsOffset++] = (byte) (nameIndex >> 8);
841
		contents[contentsOffset++] = (byte) nameIndex;
853
		contents[contentsOffset++] = (byte) nameIndex;
842
		// Then the descriptorIndex
854
		// Then the descriptorIndex
843
		int descriptorIndex = constantPool.literalIndex(fieldBinding.type.signature());
855
		int descriptorIndex = constantPool.literalIndex(fieldBinding.type);
844
		contents[contentsOffset++] = (byte) (descriptorIndex >> 8);
856
		contents[contentsOffset++] = (byte) (descriptorIndex >> 8);
845
		contents[contentsOffset++] = (byte) descriptorIndex;
857
		contents[contentsOffset++] = (byte) descriptorIndex;
846
		int fieldAttributeOffset = contentsOffset;
858
		int fieldAttributeOffset = contentsOffset;
Lines 896-926 Link Here
896
			}
908
			}
897
		}
909
		}
898
	}
910
	}
899
900
	/**
901
	 * INTERNAL USE-ONLY
902
	 * This methods stores the bindings for each inner class. They will be used to know which entries
903
	 * have to be generated for the inner classes attributes.
904
	 * @param refBinding org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding 
905
	 */
906
	private void addInnerClasses(ReferenceBinding refBinding) {
907
		// check first if that reference binding is there
908
		for (int i = 0; i < numberOfInnerClasses; i++) {
909
			if (innerClassesBindings[i] == refBinding)
910
				return;
911
		}
912
		int length = innerClassesBindings.length;
913
		if (numberOfInnerClasses == length) {
914
			System.arraycopy(
915
				innerClassesBindings,
916
				0,
917
				innerClassesBindings = new ReferenceBinding[length * 2],
918
				0,
919
				length);
920
		}
921
		innerClassesBindings[numberOfInnerClasses++] = refBinding;
922
	}
923
924
	private void addMissingAbstractProblemMethod(MethodDeclaration methodDeclaration, MethodBinding methodBinding, CategorizedProblem problem, CompilationResult compilationResult) {
911
	private void addMissingAbstractProblemMethod(MethodDeclaration methodDeclaration, MethodBinding methodBinding, CategorizedProblem problem, CompilationResult compilationResult) {
925
		// always clear the strictfp/native/abstract bit for a problem method
912
		// always clear the strictfp/native/abstract bit for a problem method
926
		generateMethodInfoHeader(methodBinding, methodBinding.modifiers & ~(ClassFileConstants.AccStrictfp | ClassFileConstants.AccNative | ClassFileConstants.AccAbstract));
913
		generateMethodInfoHeader(methodBinding, methodBinding.modifiers & ~(ClassFileConstants.AccStrictfp | ClassFileConstants.AccNative | ClassFileConstants.AccAbstract));
Lines 1532-1538 Link Here
1532
							/* represents ClassNotFoundException, see class literal access*/
1519
							/* represents ClassNotFoundException, see class literal access*/
1533
							nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangClassNotFoundExceptionConstantPoolName);
1520
							nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangClassNotFoundExceptionConstantPoolName);
1534
						} else {
1521
						} else {
1535
							nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType.constantPoolName());
1522
							nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType);
1536
						}
1523
						}
1537
						this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
1524
						this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
1538
						this.contents[localContentsOffset++] = (byte) nameIndex;
1525
						this.contents[localContentsOffset++] = (byte) nameIndex;
Lines 2212-2218 Link Here
2212
							/* represents denote ClassNotFoundException, see class literal access*/
2199
							/* represents denote ClassNotFoundException, see class literal access*/
2213
							nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangClassNotFoundExceptionConstantPoolName);
2200
							nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangClassNotFoundExceptionConstantPoolName);
2214
						} else {
2201
						} else {
2215
							nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType.constantPoolName());
2202
							nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType);
2216
						}
2203
						}
2217
						this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
2204
						this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
2218
						this.contents[localContentsOffset++] = (byte) nameIndex;
2205
						this.contents[localContentsOffset++] = (byte) nameIndex;
Lines 4407-4413 Link Here
4407
									nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangNoSuchFieldErrorConstantPoolName);
4394
									nameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangNoSuchFieldErrorConstantPoolName);
4408
									break;
4395
									break;
4409
								default:
4396
								default:
4410
									nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType.constantPoolName());
4397
									nameIndex = constantPool.literalIndexForType(exceptionLabel.exceptionType);
4411
							}
4398
							}
4412
							this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
4399
							this.contents[localContentsOffset++] = (byte) (nameIndex >> 8);
4413
							this.contents[localContentsOffset++] = (byte) nameIndex;
4400
							this.contents[localContentsOffset++] = (byte) nameIndex;
Lines 5330-5336 Link Here
5330
			contents[contentsOffset++] = (byte) (length >> 8);
5317
			contents[contentsOffset++] = (byte) (length >> 8);
5331
			contents[contentsOffset++] = (byte) length;
5318
			contents[contentsOffset++] = (byte) length;
5332
			for (int i = 0; i < length; i++) {
5319
			for (int i = 0; i < length; i++) {
5333
				int exceptionIndex = constantPool.literalIndexForType(thrownsExceptions[i].constantPoolName());
5320
				int exceptionIndex = constantPool.literalIndexForType(thrownsExceptions[i]);
5334
				contents[contentsOffset++] = (byte) (exceptionIndex >> 8);
5321
				contents[contentsOffset++] = (byte) (exceptionIndex >> 8);
5335
				contents[contentsOffset++] = (byte) exceptionIndex;
5322
				contents[contentsOffset++] = (byte) exceptionIndex;
5336
			}
5323
			}
Lines 5457-5463 Link Here
5457
		int nameIndex = constantPool.literalIndex(methodBinding.selector);
5444
		int nameIndex = constantPool.literalIndex(methodBinding.selector);
5458
		contents[contentsOffset++] = (byte) (nameIndex >> 8);
5445
		contents[contentsOffset++] = (byte) (nameIndex >> 8);
5459
		contents[contentsOffset++] = (byte) nameIndex;
5446
		contents[contentsOffset++] = (byte) nameIndex;
5460
		int descriptorIndex = constantPool.literalIndex(methodBinding.signature());
5447
		int descriptorIndex = constantPool.literalIndex(methodBinding.signature(this));
5461
		contents[contentsOffset++] = (byte) (descriptorIndex >> 8);
5448
		contents[contentsOffset++] = (byte) (descriptorIndex >> 8);
5462
		contents[contentsOffset++] = (byte) descriptorIndex;
5449
		contents[contentsOffset++] = (byte) descriptorIndex;
5463
	}
5450
	}
Lines 5832-5838 Link Here
5832
		// now we continue to generate the bytes inside the contents array
5819
		// now we continue to generate the bytes inside the contents array
5833
		contents[contentsOffset++] = (byte) (accessFlags >> 8);
5820
		contents[contentsOffset++] = (byte) (accessFlags >> 8);
5834
		contents[contentsOffset++] = (byte) accessFlags;
5821
		contents[contentsOffset++] = (byte) accessFlags;
5835
		int classNameIndex = constantPool.literalIndexForType(aType.constantPoolName());
5822
		int classNameIndex = constantPool.literalIndexForType(aType);
5836
		contents[contentsOffset++] = (byte) (classNameIndex >> 8);
5823
		contents[contentsOffset++] = (byte) (classNameIndex >> 8);
5837
		contents[contentsOffset++] = (byte) classNameIndex;
5824
		contents[contentsOffset++] = (byte) classNameIndex;
5838
		int superclassNameIndex;
5825
		int superclassNameIndex;
Lines 5840-5846 Link Here
5840
			superclassNameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangObjectConstantPoolName);
5827
			superclassNameIndex = constantPool.literalIndexForType(ConstantPool.JavaLangObjectConstantPoolName);
5841
		} else {
5828
		} else {
5842
			superclassNameIndex =
5829
			superclassNameIndex =
5843
				(aType.superclass == null ? 0 : constantPool.literalIndexForType(aType.superclass.constantPoolName()));
5830
				(aType.superclass == null ? 0 : constantPool.literalIndexForType(aType.superclass));
5844
		}
5831
		}
5845
		contents[contentsOffset++] = (byte) (superclassNameIndex >> 8);
5832
		contents[contentsOffset++] = (byte) (superclassNameIndex >> 8);
5846
		contents[contentsOffset++] = (byte) superclassNameIndex;
5833
		contents[contentsOffset++] = (byte) superclassNameIndex;
Lines 5849-5859 Link Here
5849
		contents[contentsOffset++] = (byte) (interfacesCount >> 8);
5836
		contents[contentsOffset++] = (byte) (interfacesCount >> 8);
5850
		contents[contentsOffset++] = (byte) interfacesCount;
5837
		contents[contentsOffset++] = (byte) interfacesCount;
5851
		for (int i = 0; i < interfacesCount; i++) {
5838
		for (int i = 0; i < interfacesCount; i++) {
5852
			int interfaceIndex = constantPool.literalIndexForType(superInterfacesBinding[i].constantPoolName());
5839
			int interfaceIndex = constantPool.literalIndexForType(superInterfacesBinding[i]);
5853
			contents[contentsOffset++] = (byte) (interfaceIndex >> 8);
5840
			contents[contentsOffset++] = (byte) (interfaceIndex >> 8);
5854
			contents[contentsOffset++] = (byte) interfaceIndex;
5841
			contents[contentsOffset++] = (byte) interfaceIndex;
5855
		}
5842
		}
5856
		innerClassesBindings = new ReferenceBinding[INNER_CLASSES_SIZE];
5857
		this.creatingProblemType = createProblemType;
5843
		this.creatingProblemType = createProblemType;
5858
5844
5859
		// retrieve the enclosing one guaranteed to be the one matching the propagated flow info
5845
		// retrieve the enclosing one guaranteed to be the one matching the propagated flow info
Lines 5904-5981 Link Here
5904
		return current;
5890
		return current;
5905
	}
5891
	}
5906
5892
5907
	/**
5893
	public void recordInnerClasses(TypeBinding binding) {
5908
	 * INTERNAL USE-ONLY
5894
		if (this.innerClassesBindings == null) {
5909
	 * This is used to store a new inner class. It checks that the binding @binding doesn't already exist inside the
5895
			this.innerClassesBindings = new HashSet(INNER_CLASSES_SIZE);
5910
	 * collection of inner classes. Add all the necessary classes in the right order to fit to the specifications.
5896
		}
5911
	 *
5897
		ReferenceBinding innerClass = (ReferenceBinding) binding;
5912
	 * @param binding org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding
5898
		this.innerClassesBindings.add(innerClass.erasure());
5913
	 */
5899
		ReferenceBinding enclosingType = innerClass.enclosingType();
5914
	public void recordEnclosingTypeAttributes(ReferenceBinding binding) {
5900
		while (enclosingType != null
5915
		// add all the enclosing types
5901
				&& enclosingType.isNestedType()) {
5916
		ReferenceBinding enclosingType = referenceBinding.enclosingType();
5902
			this.innerClassesBindings.add(enclosingType.erasure());
5917
		int depth = 0;
5918
		while (enclosingType != null) {
5919
			depth++;
5920
			enclosingType = enclosingType.enclosingType();
5921
		}
5922
		enclosingType = referenceBinding;
5923
		ReferenceBinding enclosingTypes[];
5924
		if (depth >= 2) {
5925
			enclosingTypes = new ReferenceBinding[depth];
5926
			for (int i = depth - 1; i >= 0; i--) {
5927
				enclosingTypes[i] = enclosingType;
5928
				enclosingType = enclosingType.enclosingType();
5929
			}
5930
			for (int i = 0; i < depth; i++) {
5931
				addInnerClasses(enclosingTypes[i]);
5932
			}
5933
		} else {
5934
			addInnerClasses(referenceBinding);
5935
		}
5936
	}
5937
5938
	/**
5939
	 * INTERNAL USE-ONLY
5940
	 * This is used to store a new inner class. It checks that the binding @binding doesn't already exist inside the
5941
	 * collection of inner classes. Add all the necessary classes in the right order to fit to the specifications.
5942
	 *
5943
	 * @param binding org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding
5944
	 */
5945
	public void recordNestedLocalAttribute(ReferenceBinding binding) {
5946
		// add all the enclosing types
5947
		ReferenceBinding enclosingType = referenceBinding.enclosingType();
5948
		int depth = 0;
5949
		while (enclosingType != null) {
5950
			depth++;
5951
			enclosingType = enclosingType.enclosingType();
5903
			enclosingType = enclosingType.enclosingType();
5952
		}
5904
		}
5953
		enclosingType = referenceBinding;
5954
		ReferenceBinding enclosingTypes[];
5955
		if (depth >= 2) {
5956
			enclosingTypes = new ReferenceBinding[depth];
5957
			for (int i = depth - 1; i >= 0; i--) {
5958
				enclosingTypes[i] = enclosingType;
5959
				enclosingType = enclosingType.enclosingType();
5960
			}
5961
			for (int i = 0; i < depth; i++)
5962
				addInnerClasses(enclosingTypes[i]);
5963
		} else {
5964
			addInnerClasses(binding);
5965
		}
5966
	}
5905
	}
5967
5906
5968
	/**
5969
	 * INTERNAL USE-ONLY
5970
	 * This is used to store a new inner class. It checks that the binding @binding doesn't already exist inside the
5971
	 * collection of inner classes. Add all the necessary classes in the right order to fit to the specifications.
5972
	 *
5973
	 * @param binding org.eclipse.jdt.internal.compiler.lookup.ReferenceBinding
5974
	 */
5975
	public void recordNestedMemberAttribute(ReferenceBinding binding) {
5976
		addInnerClasses(binding);
5977
	}
5978
	
5979
	public void reset(SourceTypeBinding typeBinding) {
5907
	public void reset(SourceTypeBinding typeBinding) {
5980
		// the code stream is reinitialized for each method
5908
		// the code stream is reinitialized for each method
5981
		final CompilerOptions options = typeBinding.scope.compilerOptions();
5909
		final CompilerOptions options = typeBinding.scope.compilerOptions();
Lines 5995-6001 Link Here
5995
		this.headerOffset = 0;
5923
		this.headerOffset = 0;
5996
		this.methodCount = 0;
5924
		this.methodCount = 0;
5997
		this.methodCountOffset = 0;
5925
		this.methodCountOffset = 0;
5998
		this.numberOfInnerClasses = 0;
5926
		if (this.innerClassesBindings != null) {
5927
			this.innerClassesBindings.clear();
5928
		}
5999
	}
5929
	}
6000
5930
6001
	/**
5931
	/**
(-)compiler/org/eclipse/jdt/internal/compiler/codegen/CodeStream.java (-22 / +32 lines)
Lines 339-345 Link Here
339
	}
339
	}
340
	position++;
340
	position++;
341
	bCodeStream[classFileOffset++] = Opcodes.OPC_anewarray;
341
	bCodeStream[classFileOffset++] = Opcodes.OPC_anewarray;
342
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding.constantPoolName()));
342
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding));
343
}
343
}
344
public void areturn() {
344
public void areturn() {
345
	if (DEBUG) System.out.println(position + "\t\tareturn"); //$NON-NLS-1$
345
	if (DEBUG) System.out.println(position + "\t\tareturn"); //$NON-NLS-1$
Lines 615-621 Link Here
615
	}
615
	}
616
	position++;
616
	position++;
617
	bCodeStream[classFileOffset++] = Opcodes.OPC_checkcast;
617
	bCodeStream[classFileOffset++] = Opcodes.OPC_checkcast;
618
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding.constantPoolName()));
618
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding));
619
}
619
}
620
public void d2f() {
620
public void d2f() {
621
	if (DEBUG) System.out.println(position + "\t\td2f"); //$NON-NLS-1$
621
	if (DEBUG) System.out.println(position + "\t\td2f"); //$NON-NLS-1$
Lines 1903-1908 Link Here
1903
	bCodeStream[classFileOffset++] = opcode;
1903
	bCodeStream[classFileOffset++] = opcode;
1904
	writeUnsignedShort(constantPool.literalIndexForField(declaringClass, name, signature));
1904
	writeUnsignedShort(constantPool.literalIndexForField(declaringClass, name, signature));
1905
}
1905
}
1906
private void generateFieldAccess(byte opcode, int returnTypeSize, ReferenceBinding binding, char[] name, TypeBinding type) {
1907
	if (binding.isNestedType()) {
1908
		this.classFile.recordInnerClasses(binding);
1909
	}
1910
	TypeBinding leafComponentType = type.leafComponentType();
1911
	if (leafComponentType.isNestedType()) {
1912
		this.classFile.recordInnerClasses(leafComponentType);
1913
	}
1914
	this.generateFieldAccess(opcode, returnTypeSize, binding.constantPoolName(), name, type.signature());
1915
}
1906
/**
1916
/**
1907
 * Generates the sequence of instructions which will perform the conversion of the expression
1917
 * Generates the sequence of instructions which will perform the conversion of the expression
1908
 * on the stack into a different type (e.g. long l = someInt; --> i2l must be inserted).
1918
 * on the stack into a different type (e.g. long l = someInt; --> i2l must be inserted).
Lines 2835-2843 Link Here
2835
	generateFieldAccess(
2845
	generateFieldAccess(
2836
			Opcodes.OPC_getfield,
2846
			Opcodes.OPC_getfield,
2837
			returnTypeSize,
2847
			returnTypeSize,
2838
			fieldBinding.declaringClass.constantPoolName(),
2848
			fieldBinding.declaringClass,
2839
			fieldBinding.name,
2849
			fieldBinding.name,
2840
			fieldBinding.type.signature());
2850
			fieldBinding.type);
2841
}
2851
}
2842
protected int getPosition() {
2852
protected int getPosition() {
2843
	return this.position;
2853
	return this.position;
Lines 2851-2859 Link Here
2851
	generateFieldAccess(
2861
	generateFieldAccess(
2852
			Opcodes.OPC_getstatic,
2862
			Opcodes.OPC_getstatic,
2853
			returnTypeSize,
2863
			returnTypeSize,
2854
			fieldBinding.declaringClass.constantPoolName(),
2864
			fieldBinding.declaringClass,
2855
			fieldBinding.name,
2865
			fieldBinding.name,
2856
			fieldBinding.type.signature());
2866
			fieldBinding.type);
2857
}
2867
}
2858
public void getTYPE(int baseTypeID) {
2868
public void getTYPE(int baseTypeID) {
2859
	countLabels = 0;
2869
	countLabels = 0;
Lines 3712-3718 Link Here
3712
	}
3722
	}
3713
	position++;
3723
	position++;
3714
	bCodeStream[classFileOffset++] = Opcodes.OPC_instanceof;
3724
	bCodeStream[classFileOffset++] = Opcodes.OPC_instanceof;
3715
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding.constantPoolName()));
3725
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding));
3716
}
3726
}
3717
protected void invoke(int opcode, int argsSize, int returnTypeSize, char[] declaringClass, char[] selector, char[] signature) {
3727
protected void invoke(int opcode, int argsSize, int returnTypeSize, char[] declaringClass, char[] selector, char[] signature) {
3718
	countLabels = 0;
3728
	countLabels = 0;
Lines 3837-3845 Link Here
3837
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokeinterface;
3847
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokeinterface;
3838
	writeUnsignedShort(
3848
	writeUnsignedShort(
3839
		constantPool.literalIndexForMethod(
3849
		constantPool.literalIndexForMethod(
3840
			methodBinding.constantPoolDeclaringClass().constantPoolName(),
3850
			methodBinding.constantPoolDeclaringClass(),
3841
			methodBinding.selector,
3851
			methodBinding.selector,
3842
			methodBinding.signature(),
3852
			methodBinding.signature(classFile),
3843
			true));
3853
			true));
3844
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
3854
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
3845
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
3855
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
Lines 4135-4143 Link Here
4135
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokespecial;
4145
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokespecial;
4136
	writeUnsignedShort(
4146
	writeUnsignedShort(
4137
		constantPool.literalIndexForMethod(
4147
		constantPool.literalIndexForMethod(
4138
			methodBinding.constantPoolDeclaringClass().constantPoolName(),
4148
			methodBinding.constantPoolDeclaringClass(),
4139
			methodBinding.selector,
4149
			methodBinding.selector,
4140
			methodBinding.signature(),
4150
			methodBinding.signature(classFile),
4141
			false));
4151
			false));
4142
	if (methodBinding.isConstructor()) {
4152
	if (methodBinding.isConstructor()) {
4143
		final ReferenceBinding declaringClass = methodBinding.declaringClass;
4153
		final ReferenceBinding declaringClass = methodBinding.declaringClass;
Lines 4198-4206 Link Here
4198
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokestatic;
4208
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokestatic;
4199
	writeUnsignedShort(
4209
	writeUnsignedShort(
4200
		constantPool.literalIndexForMethod(
4210
		constantPool.literalIndexForMethod(
4201
			methodBinding.constantPoolDeclaringClass().constantPoolName(),
4211
			methodBinding.constantPoolDeclaringClass(),
4202
			methodBinding.selector,
4212
			methodBinding.selector,
4203
			methodBinding.signature(),
4213
			methodBinding.signature(classFile),
4204
			false));
4214
			false));
4205
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
4215
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
4206
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
4216
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
Lines 4472-4480 Link Here
4472
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokevirtual;
4482
	bCodeStream[classFileOffset++] = Opcodes.OPC_invokevirtual;
4473
	writeUnsignedShort(
4483
	writeUnsignedShort(
4474
		constantPool.literalIndexForMethod(
4484
		constantPool.literalIndexForMethod(
4475
			methodBinding.constantPoolDeclaringClass().constantPoolName(),
4485
			methodBinding.constantPoolDeclaringClass(),
4476
			methodBinding.selector,
4486
			methodBinding.selector,
4477
			methodBinding.signature(),
4487
			methodBinding.signature(classFile),
4478
			false));
4488
			false));
4479
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
4489
	for (int i = methodBinding.parameters.length - 1; i >= 0; i--)
4480
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
4490
		if (((id = methodBinding.parameters[i].id) == TypeIds.T_double) || (id == TypeIds.T_long))
Lines 4949-4955 Link Here
4949
}
4959
}
4950
public void ldc(TypeBinding typeBinding) {
4960
public void ldc(TypeBinding typeBinding) {
4951
	countLabels = 0;
4961
	countLabels = 0;
4952
	int index = constantPool.literalIndexForType(typeBinding.constantPoolName());
4962
	int index = constantPool.literalIndexForType(typeBinding);
4953
	stackDepth++;
4963
	stackDepth++;
4954
	if (stackDepth > stackMax)
4964
	if (stackDepth > stackMax)
4955
		stackMax = stackDepth;
4965
		stackMax = stackDepth;
Lines 5464-5470 Link Here
5464
	}
5474
	}
5465
	position += 2;
5475
	position += 2;
5466
	bCodeStream[classFileOffset++] = Opcodes.OPC_multianewarray;
5476
	bCodeStream[classFileOffset++] = Opcodes.OPC_multianewarray;
5467
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding.constantPoolName()));
5477
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding));
5468
	bCodeStream[classFileOffset++] = (byte) dimensions;
5478
	bCodeStream[classFileOffset++] = (byte) dimensions;
5469
}
5479
}
5470
// We didn't call it new, because there is a conflit with the new keyword
5480
// We didn't call it new, because there is a conflit with the new keyword
Lines 5479-5485 Link Here
5479
	}
5489
	}
5480
	position++;
5490
	position++;
5481
	bCodeStream[classFileOffset++] = Opcodes.OPC_new;
5491
	bCodeStream[classFileOffset++] = Opcodes.OPC_new;
5482
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding.constantPoolName()));
5492
	writeUnsignedShort(constantPool.literalIndexForType(typeBinding));
5483
}
5493
}
5484
public void newarray(int array_Type) {
5494
public void newarray(int array_Type) {
5485
	if (DEBUG) System.out.println(position + "\t\tnewarray:"+array_Type); //$NON-NLS-1$
5495
	if (DEBUG) System.out.println(position + "\t\tnewarray:"+array_Type); //$NON-NLS-1$
Lines 5702-5710 Link Here
5702
	generateFieldAccess(
5712
	generateFieldAccess(
5703
			Opcodes.OPC_putfield,
5713
			Opcodes.OPC_putfield,
5704
			returnTypeSize,
5714
			returnTypeSize,
5705
			fieldBinding.declaringClass.constantPoolName(),
5715
			fieldBinding.declaringClass,
5706
			fieldBinding.name,
5716
			fieldBinding.name,
5707
			fieldBinding.type.signature());
5717
			fieldBinding.type);
5708
}
5718
}
5709
public void putstatic(FieldBinding fieldBinding) {
5719
public void putstatic(FieldBinding fieldBinding) {
5710
	if (DEBUG) System.out.println(position + "\t\tputstatic:"+fieldBinding); //$NON-NLS-1$
5720
	if (DEBUG) System.out.println(position + "\t\tputstatic:"+fieldBinding); //$NON-NLS-1$
Lines 5715-5723 Link Here
5715
	generateFieldAccess(
5725
	generateFieldAccess(
5716
			Opcodes.OPC_putstatic,
5726
			Opcodes.OPC_putstatic,
5717
			returnTypeSize,
5727
			returnTypeSize,
5718
			fieldBinding.declaringClass.constantPoolName(),
5728
			fieldBinding.declaringClass,
5719
			fieldBinding.name,
5729
			fieldBinding.name,
5720
			fieldBinding.type.signature());
5730
			fieldBinding.type);
5721
}
5731
}
5722
public void record(LocalVariableBinding local) {
5732
public void record(LocalVariableBinding local) {
5723
	if ((this.generateAttributes & (ClassFileConstants.ATTR_VARS | ClassFileConstants.ATTR_STACK_MAP)) == 0)
5733
	if ((this.generateAttributes & (ClassFileConstants.ATTR_VARS | ClassFileConstants.ATTR_STACK_MAP)) == 0)
(-)compiler/org/eclipse/jdt/internal/compiler/codegen/ConstantPool.java (-4 / +26 lines)
Lines 13-18 Link Here
13
import org.eclipse.jdt.core.compiler.CharOperation;
13
import org.eclipse.jdt.core.compiler.CharOperation;
14
import org.eclipse.jdt.internal.compiler.ClassFile;
14
import org.eclipse.jdt.internal.compiler.ClassFile;
15
import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
15
import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
16
import org.eclipse.jdt.internal.compiler.lookup.TypeBinding;
16
import org.eclipse.jdt.internal.compiler.lookup.TypeConstants;
17
import org.eclipse.jdt.internal.compiler.lookup.TypeConstants;
17
import org.eclipse.jdt.internal.compiler.lookup.TypeIds;
18
import org.eclipse.jdt.internal.compiler.lookup.TypeIds;
18
import org.eclipse.jdt.internal.compiler.util.HashtableOfObject;
19
import org.eclipse.jdt.internal.compiler.util.HashtableOfObject;
Lines 285-290 Link Here
285
	}
286
	}
286
	return index;
287
	return index;
287
}
288
}
289
public int literalIndex(TypeBinding binding) {
290
	TypeBinding typeBinding = binding.leafComponentType();
291
	if (typeBinding.isNestedType()) {
292
		this.classFile.recordInnerClasses(typeBinding);
293
	}
294
	return literalIndex(binding.signature());
295
}
288
/**
296
/**
289
 * This method returns the index into the constantPool corresponding to the type descriptor.
297
 * This method returns the index into the constantPool corresponding to the type descriptor.
290
 *
298
 *
Lines 551-560 Link Here
551
	}
559
	}
552
	return index;
560
	return index;
553
}
561
}
554
/**
555
 * This method returns the index into the constantPool corresponding to the type descriptor 
556
 * corresponding to a type constant pool name.
557
 */
558
public int literalIndexForType(final char[] constantPoolName) {
562
public int literalIndexForType(final char[] constantPoolName) {
559
	int index;
563
	int index;
560
	if ((index = classCache.putIfAbsent(constantPoolName, this.currentIndex)) < 0) {
564
	if ((index = classCache.putIfAbsent(constantPoolName, this.currentIndex)) < 0) {
Lines 577-582 Link Here
577
	}
581
	}
578
	return index;
582
	return index;
579
}
583
}
584
/*
585
 * This method returns the index into the constantPool corresponding to the type descriptor 
586
 * corresponding to a type constant pool name
587
 * binding must not be an array type.
588
 */
589
public int literalIndexForType(final TypeBinding binding) {
590
	TypeBinding typeBinding = binding.leafComponentType();
591
	if (typeBinding.isNestedType()) {
592
		this.classFile.recordInnerClasses(typeBinding);
593
	}
594
	return this.literalIndexForType(binding.constantPoolName());
595
}
580
public int literalIndexForMethod(char[] declaringClass, char[] selector, char[] signature, boolean isInterface) {
596
public int literalIndexForMethod(char[] declaringClass, char[] selector, char[] signature, boolean isInterface) {
581
	int index;
597
	int index;
582
	if ((index = putInCacheIfAbsent(declaringClass, selector, signature, this.currentIndex)) < 0) {
598
	if ((index = putInCacheIfAbsent(declaringClass, selector, signature, this.currentIndex)) < 0) {
Lines 605-610 Link Here
605
	}
621
	}
606
	return index;
622
	return index;
607
}
623
}
624
public int literalIndexForMethod(TypeBinding binding, char[] selector, char[] signature, boolean isInterface) {
625
	if (binding.isNestedType()) {
626
		this.classFile.recordInnerClasses(binding);
627
	}
628
	return this.literalIndexForMethod(binding.constantPoolName(), selector, signature, isInterface);
629
}
608
public int literalIndexForNameAndType(char[] name, char[] signature) {
630
public int literalIndexForNameAndType(char[] name, char[] signature) {
609
	int index;
631
	int index;
610
	if ((index = putInNameAndTypeCacheIfAbsent(name, signature, currentIndex)) < 0) {
632
	if ((index = putInNameAndTypeCacheIfAbsent(name, signature, currentIndex)) < 0) {
(-)compiler/org/eclipse/jdt/core/compiler/CharOperation.java (-1 / +24 lines)
Lines 484-490 Link Here
484
	result[length] = second;
484
	result[length] = second;
485
	return result;
485
	return result;
486
}
486
}
487
487
/**
488
 * Compares the two char arrays lexicographically.
489
 *
490
 * Returns a negative integer if array1 lexicographically precedes the array2,
491
 * a positive integer if this array1 lexicographically follows the array2, or 
492
 * zero if both arrays are equal. 
493
 * 
494
 * @param array1 the first given array
495
 * @param array2 the second given array
496
 * @return the returned value of the comparison between array1 and array2
497
 * @throws NullPointerException if one of the arrays is null
498
 * @since 3.3
499
 */
500
public static final int compareTo(char[] array1, char[] array2) {
501
	int length1 = array1.length;
502
	int length2 = array2.length;
503
	int min = Math.min(length1, length2);
504
	for (int i = 0; i < min; i++) {
505
		if (array1[i] != array2[i]) {
506
			return array1[i] - array2[i];
507
		}
508
	}
509
	return length1 - length2;
510
}
488
/**
511
/**
489
 * Compares the contents of the two arrays array and prefix. Returns
512
 * Compares the contents of the two arrays array and prefix. Returns
490
 * <ul>
513
 * <ul>

Return to bug 171184