1 11 package org.eclipse.jdt.internal.codeassist.impl; 12 13 import java.util.Map ; 14 15 import org.eclipse.jdt.core.compiler.CharOperation; 16 import org.eclipse.jdt.internal.compiler.*; 17 import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants; 18 import org.eclipse.jdt.internal.compiler.env.*; 19 20 import org.eclipse.jdt.internal.compiler.ast.*; 21 import org.eclipse.jdt.internal.compiler.lookup.*; 22 import org.eclipse.jdt.internal.compiler.parser.*; 23 import org.eclipse.jdt.internal.compiler.problem.ProblemSeverities; 24 import org.eclipse.jdt.internal.compiler.impl.*; 25 import org.eclipse.jdt.internal.core.NameLookup; 26 import org.eclipse.jdt.internal.core.SearchableEnvironment; 27 28 public abstract class Engine implements ITypeRequestor { 29 30 public LookupEnvironment lookupEnvironment; 31 32 protected CompilationUnitScope unitScope; 33 public SearchableEnvironment nameEnvironment; 34 35 public AssistOptions options; 36 public CompilerOptions compilerOptions; 37 public boolean forbiddenReferenceIsError; 38 public boolean discouragedReferenceIsError; 39 40 public boolean importCachesInitialized = false; 41 public char[][][] importsCache; 42 public ImportBinding[] onDemandImportsCache; 43 public int importCacheCount = 0; 44 public int onDemandImportCacheCount = 0; 45 public char[] currentPackageName = null; 46 47 public Engine(Map settings){ 48 this.options = new AssistOptions(settings); 49 this.compilerOptions = new CompilerOptions(settings); 50 this.forbiddenReferenceIsError = 51 (this.compilerOptions.getSeverity(CompilerOptions.ForbiddenReference) & ProblemSeverities.Error) != 0; 52 this.discouragedReferenceIsError = 53 (this.compilerOptions.getSeverity(CompilerOptions.DiscouragedReference) & ProblemSeverities.Error) != 0; 54 } 55 56 59 public void accept(IBinaryType binaryType, PackageBinding packageBinding, AccessRestriction accessRestriction) { 60 lookupEnvironment.createBinaryTypeFrom(binaryType, packageBinding, accessRestriction); 61 } 62 63 66 public void accept(ICompilationUnit sourceUnit, AccessRestriction accessRestriction) { 67 CompilationResult result = new CompilationResult(sourceUnit, 1, 1, this.compilerOptions.maxProblemsPerUnit); 68 CompilationUnitDeclaration parsedUnit = 69 this.getParser().dietParse(sourceUnit, result); 70 71 lookupEnvironment.buildTypeBindings(parsedUnit, accessRestriction); 72 lookupEnvironment.completeTypeBindings(parsedUnit, true); 73 } 74 75 79 public void accept(ISourceType[] sourceTypes, PackageBinding packageBinding, AccessRestriction accessRestriction) { 80 CompilationResult result = 81 new CompilationResult(sourceTypes[0].getFileName(), 1, 1, this.compilerOptions.maxProblemsPerUnit); 82 CompilationUnitDeclaration unit = 83 SourceTypeConverter.buildCompilationUnit( 84 sourceTypes, SourceTypeConverter.FIELD_AND_METHOD | SourceTypeConverter.MEMBER_TYPE, lookupEnvironment.problemReporter, 89 result); 90 91 if (unit != null) { 92 lookupEnvironment.buildTypeBindings(unit, accessRestriction); 93 lookupEnvironment.completeTypeBindings(unit, true); 94 } 95 } 96 97 public abstract AssistParser getParser(); 98 99 public void initializeImportCaches() { 100 ImportBinding[] importBindings = this.unitScope.imports; 101 int length = importBindings == null ? 0 : importBindings.length; 102 103 this.currentPackageName = CharOperation.concatWith(unitScope.fPackage.compoundName, '.'); 104 105 for (int i = 0; i < length; i++) { 106 ImportBinding importBinding = importBindings[i]; 107 if(importBinding.onDemand) { 108 if(this.onDemandImportsCache == null) { 109 this.onDemandImportsCache = new ImportBinding[length - i]; 110 } 111 this.onDemandImportsCache[this.onDemandImportCacheCount++] = 112 importBinding; 113 } else { 114 if(!(importBinding.resolvedImport instanceof MethodBinding) || 115 importBinding instanceof ImportConflictBinding) { 116 if(this.importsCache == null) { 117 this.importsCache = new char[length - i][][]; 118 } 119 this.importsCache[this.importCacheCount++] = new char[][]{ 120 importBinding.compoundName[importBinding.compoundName.length - 1], 121 CharOperation.concatWith(importBinding.compoundName, '.') 122 }; 123 } 124 } 125 } 126 127 this.importCachesInitialized = true; 128 } 129 130 protected boolean mustQualifyType( 131 char[] packageName, 132 char[] typeName, 133 char[] enclosingTypeNames, 134 int modifiers) { 135 136 if (unitScope == null) 138 return true; 139 140 if(!this.importCachesInitialized) { 141 this.initializeImportCaches(); 142 } 143 144 for (int i = 0; i < this.importCacheCount; i++) { 145 char[][] importName = this.importsCache[i]; 146 if(CharOperation.equals(typeName, importName[0])) { 147 char[] fullyQualifiedTypeName = 148 enclosingTypeNames == null || enclosingTypeNames.length == 0 149 ? CharOperation.concat( 150 packageName, 151 typeName, 152 '.') 153 : CharOperation.concat( 154 CharOperation.concat( 155 packageName, 156 enclosingTypeNames, 157 '.'), 158 typeName, 159 '.'); 160 return !CharOperation.equals(fullyQualifiedTypeName, importName[1]); 161 } 162 } 163 164 if ((enclosingTypeNames == null || enclosingTypeNames.length == 0 ) && CharOperation.equals(this.currentPackageName, packageName)) 165 return false; 166 167 char[] fullyQualifiedEnclosingTypeName = null; 168 169 for (int i = 0; i < this.onDemandImportCacheCount; i++) { 170 ImportBinding importBinding = this.onDemandImportsCache[i]; 171 Binding resolvedImport = importBinding.resolvedImport; 172 173 char[][] importName = importBinding.compoundName; 174 char[] importFlatName = CharOperation.concatWith(importName, '.'); 175 176 boolean isFound = false; 177 if(resolvedImport instanceof ReferenceBinding) { 179 if(enclosingTypeNames != null && enclosingTypeNames.length != 0) { 180 if(fullyQualifiedEnclosingTypeName == null) { 181 fullyQualifiedEnclosingTypeName = 182 CharOperation.concat( 183 packageName, 184 enclosingTypeNames, 185 '.'); 186 } 187 if(CharOperation.equals(fullyQualifiedEnclosingTypeName, importFlatName)) { 188 if(importBinding.isStatic()) { 189 isFound = (modifiers & ClassFileConstants.AccStatic) != 0; 190 } else { 191 isFound = true; 192 } 193 } 194 } 195 } else { 196 if(enclosingTypeNames == null || enclosingTypeNames.length == 0) { 197 if(CharOperation.equals(packageName, importFlatName)) { 198 if(importBinding.isStatic()) { 199 isFound = (modifiers & ClassFileConstants.AccStatic) != 0; 200 } else { 201 isFound = true; 202 } 203 } 204 } 205 } 206 207 if(isFound) { 209 for (int j = 0; j < this.onDemandImportCacheCount; j++) { 210 if(i != j) { 211 ImportBinding conflictingImportBinding = this.onDemandImportsCache[j]; 212 if(conflictingImportBinding.resolvedImport instanceof ReferenceBinding) { 213 ReferenceBinding refBinding = 214 (ReferenceBinding) conflictingImportBinding.resolvedImport; 215 if (refBinding.getMemberType(typeName) != null) { 216 return true; 217 } 218 } else { 219 char[] conflictingImportName = 220 CharOperation.concatWith(conflictingImportBinding.compoundName, '.'); 221 222 if (this.nameEnvironment.nameLookup.findType( 223 String.valueOf(typeName), 224 String.valueOf(conflictingImportName), 225 false, 226 NameLookup.ACCEPT_ALL, 227 false) != null) { 228 return true; 229 } 230 } 231 } 232 } 233 return false; 234 } 235 } 236 return true; 237 } 238 239 244 protected ASTNode parseBlockStatements(CompilationUnitDeclaration unit, int position) { 245 int length = unit.types.length; 246 for (int i = 0; i < length; i++) { 247 TypeDeclaration type = unit.types[i]; 248 if (type.declarationSourceStart < position 249 && type.declarationSourceEnd >= position) { 250 getParser().scanner.setSource(unit.compilationResult); 251 return parseBlockStatements(type, unit, position); 252 } 253 } 254 return null; 255 } 256 257 private ASTNode parseBlockStatements( 258 TypeDeclaration type, 259 CompilationUnitDeclaration unit, 260 int position) { 261 TypeDeclaration[] memberTypes = type.memberTypes; 263 if (memberTypes != null) { 264 int length = memberTypes.length; 265 for (int i = 0; i < length; i++) { 266 TypeDeclaration memberType = memberTypes[i]; 267 if (memberType.bodyStart > position) 268 continue; 269 if (memberType.declarationSourceEnd >= position) { 270 return parseBlockStatements(memberType, unit, position); 271 } 272 } 273 } 274 AbstractMethodDeclaration[] methods = type.methods; 276 if (methods != null) { 277 int length = methods.length; 278 for (int i = 0; i < length; i++) { 279 AbstractMethodDeclaration method = methods[i]; 280 if (method.bodyStart > position) 281 continue; 282 283 if(method.isDefaultConstructor()) 284 continue; 285 286 if (method.declarationSourceEnd >= position) { 287 288 getParser().parseBlockStatements(method, unit); 289 return method; 290 } 291 } 292 } 293 FieldDeclaration[] fields = type.fields; 295 if (fields != null) { 296 int length = fields.length; 297 for (int i = 0; i < length; i++) { 298 FieldDeclaration field = fields[i]; 299 if (field.sourceStart > position) 300 continue; 301 if (field.declarationSourceEnd >= position) { 302 if (field instanceof Initializer) { 303 getParser().parseBlockStatements((Initializer)field, type, unit); 304 } 305 return field; 306 } 307 } 308 } 309 return null; 310 } 311 312 protected void reset() { 313 lookupEnvironment.reset(); 314 } 315 316 public static char[] getTypeSignature(TypeBinding typeBinding) { 317 return typeBinding.signature(); 318 } 319 public static char[] getSignature(Binding binding) { 320 char[] result = null; 321 if ((binding.kind() & Binding.TYPE) != 0) { 322 TypeBinding typeBinding = (TypeBinding)binding; 323 result = typeBinding.genericTypeSignature(); 324 } else if ((binding.kind() & Binding.METHOD) != 0) { 325 MethodBinding methodBinding = (MethodBinding)binding; 326 int oldMod = methodBinding.modifiers; 327 methodBinding.modifiers |= ExtraCompilerModifiers.AccGenericSignature; 329 result = methodBinding.genericSignature(); 330 if(result == null) { 331 result = methodBinding.signature(); 332 } 333 methodBinding.modifiers = oldMod; 334 } 335 if (result != null) { 336 result = CharOperation.replaceOnCopy(result, '/', '.'); 337 } 338 return result; 339 } 340 341 public static char[][] getSignatures(Binding[] bindings) { 342 int length = bindings == null ? 0 : bindings.length; 343 char[][] signatures = new char[length][]; 344 for (int i = 0; i < length; i++) { 345 signatures[i] = getSignature(bindings[i]); 346 } 347 return signatures; 348 } 349 } 350 | Popular Tags |