public void locateMatches(SearchDocument[] indexMatches, SearchPattern pattern, IJavaSearchScope scope, SearchRequestor requestor, IProgressMonitor monitor) throws CoreException { MatchLocator matchLocator = new MatchLocator( pattern, requestor, scope, monitor ); /* eliminating false matches and locating them */ if (monitor != null && monitor.isCanceled()) throw new OperationCanceledException(); matchLocator.locateMatches(indexMatches); }
protected void locateMatches(JavaProject javaProject, PossibleMatch[] possibleMatches, int start, int length) throws CoreException { initialize(javaProject, length); for (int i = start, maxUnits = start + length; i < maxUnits; i++) { PossibleMatch possibleMatch = possibleMatches[i]; if (skipMatch(javaProject, possibleMatch)) continue; try { if (!parseAndBuildBindings(possibleMatch, mustResolvePattern)) continue; if ((this.progressWorked%this.progressStep)==0) this.progressMonitor.worked(this.progressStep); process(possibleMatch, bindingsWereCreated); if (this.numberOfMatches>0 && this.matchesToProcess[this.numberOfMatches-1] == possibleMatch) { IType focusType = getFocusType(); if (focusType == null) { this.hierarchyResolver = null; } else if (!createHierarchyResolver(focusType, possibleMatches)) { if (computeSuperTypeNames(focusType) == null) return; this.matchesToProcess[i] = null; // release reference to processed possible match try { process(possibleMatch, bindingsWereCreated); } catch (AbortCompilation e) {
private IJavaElement[] createHandles(FieldDeclaration[] fields, TypeDeclaration type, IJavaElement parent) { IJavaElement[] otherElements = null; if (fields != null) { int length = fields.length; int size = 0; while (size<length && fields[size] != null) { size++; } otherElements = new IJavaElement[size]; for (int j=0; j<size; j++) { otherElements[j] = createHandle(fields[j], type, parent); } } return otherElements; } /*
IJavaElement enclosingElement = null; if (accuracy > -1) { enclosingElement = createHandle(field, type, parent); if (encloses(enclosingElement)) { int offset = field.sourceStart; SearchMatch match = newDeclarationMatch(enclosingElement, field.binding, accuracy, offset, field.sourceEnd-offset+1); if (field.initialization instanceof AllocationExpression) { reportAccurateEnumConstructorReference(match, field, (AllocationExpression) field.initialization); } else { report(match); enclosingElement = createHandle(field, type, parent); boolean report = (this.matchContainer & PatternLocator.FIELD_CONTAINER) != 0 && encloses(enclosingElement); MemberDeclarationVisitor declarationVisitor = new MemberDeclarationVisitor(enclosingElement, report ? nodes : null, nodeSet, this, typeInHierarchy); try { if (field.annotations != null) { if (enclosingElement == null) { enclosingElement = createHandle(field, type, parent); otherElements = createHandles(otherFields, type, parent); reportMatching(field.annotations, enclosingElement, otherElements, field.binding, nodeSet, true, true); } else { if (enclosingElement == null) enclosingElement = createHandle(field, type, parent); if (encloses(enclosingElement)) {
protected void reportDeclaration(MethodBinding methodBinding, MatchLocator locator, SimpleSet knownMethods) throws CoreException { ReferenceBinding declaringClass = methodBinding.declaringClass; IType type = locator.lookupType(declaringClass); if (type == null) return; // case of a secondary type method = locator.createBinaryMethodHandle(type, methodBinding.selector, parameterTypes); if (method == null || knownMethods.addIfNotIncluded(method) == null) return; if (resource == null) resource = type.getJavaProject().getProject(); IBinaryType info = locator.getBinaryInfo((org.eclipse.jdt.internal.core.ClassFile)type.getClassFile(), resource); locator.reportBinaryMemberDeclaration(resource, method, methodBinding, info, SearchMatch.A_ACCURATE); return; this.match = new MethodDeclarationMatch(method, SearchMatch.A_ACCURATE, offset, methodDecl.sourceEnd-offset+1, locator.getParticipant(), resource); locator.report(this.match);
enclosingElement = createHandle(lambdaExpression, parent); if (enclosingElement != null) { // skip if unable to find method if (encloses(enclosingElement)) { SearchMatch match = null; int length = lambdaExpression.arrowPosition() + 1 - nameSourceStart; match = this.patternLocator.newDeclarationMatch(lambdaExpression, enclosingElement, null, accuracy, length, this); if (match != null) { report(match); enclosingElement = createHandle(lambdaExpression, parent); boolean report = (this.matchContainer & PatternLocator.METHOD_CONTAINER) != 0 && encloses(enclosingElement); MemberDeclarationVisitor declarationVisitor = new MemberDeclarationVisitor(enclosingElement, report ? nodes : null, nodeSet, this, typeInHierarchy);
ClassFileReader reader = classFileReader(type); if (reader != null) { IMethod binaryMethod = createBinaryMethodHandle(type, method.selector, argumentTypeNames); if (binaryMethod == null) { while (similarMatch != null) { type = ((ClassFile)similarMatch.openable).getType(); binaryMethod = createBinaryMethodHandle(type, method.selector, argumentTypeNames); if (binaryMethod != null) { return binaryMethod; return createMethodHandle(type, new String(method.selector), parameterTypeSignatures);
protected boolean createHierarchyResolver(IType focusType, PossibleMatch[] possibleMatches) { // cache focus type if not a possible match char[][] compoundName = CharOperation.splitOn('.', focusType.getFullyQualifiedName().toCharArray()); boolean isPossibleMatch = false; for (int i = 0, length = possibleMatches.length; i < length; i++) { if (CharOperation.equals(possibleMatches[i].compoundName, compoundName)) { isPossibleMatch = true; break; } } if (!isPossibleMatch) { if (focusType.isBinary()) { try { cacheBinaryType(focusType, null); } catch (JavaModelException e) { return false; } } else { // cache all types in the focus' compilation unit (even secondary types) accept((ICompilationUnit) focusType.getCompilationUnit(), null /*TODO no access restriction*/); } } // resolve focus type this.hierarchyResolver = new HierarchyResolver(this.lookupEnvironment, null/*hierarchy is not going to be computed*/); ReferenceBinding binding = this.hierarchyResolver.setFocusType(compoundName); return binding != null && binding.isValidBinding() && (binding.tagBits & TagBits.HierarchyHasProblems) == 0; } /**
protected BinaryTypeBinding cacheBinaryType(IType type, IBinaryType binaryType) throws JavaModelException { IType enclosingType = type.getDeclaringType(); if (enclosingType != null) cacheBinaryType(enclosingType, null); // cache enclosing types first, so that binary type can be found in lookup enviroment if (binaryType == null) { ClassFile classFile = (ClassFile) type.getClassFile(); try { binaryType = getBinaryInfo(classFile, classFile.resource()); } catch (CoreException e) { if (e instanceof JavaModelException) { throw (JavaModelException) e; } else { throw new JavaModelException(e); } } } BinaryTypeBinding binding = this.lookupEnvironment.cacheBinaryType(binaryType, null /*no access restriction*/); if (binding == null) { // it was already cached as a result of a previous query char[][] compoundName = CharOperation.splitOn('.', type.getFullyQualifiedName().toCharArray()); ReferenceBinding referenceBinding = this.lookupEnvironment.getCachedType(compoundName); if (referenceBinding != null && (referenceBinding instanceof BinaryTypeBinding)) binding = (BinaryTypeBinding) referenceBinding; // if the binding could be found and if it comes from a binary type } return binding; } /*
IMethod createBinaryMethodHandle(IType type, char[] methodSelector, char[][] argumentTypeNames) { IBinaryType reader = MatchLocator.classFileReader(type); if (reader != null) { IBinaryMethod[] methods = reader.getMethods(); if (methods != null) { int argCount = argumentTypeNames == null ? 0 : argumentTypeNames.length; nextMethod : for (int i = 0, methodsLength = methods.length; i < methodsLength; i++) { IBinaryMethod binaryMethod = methods[i]; char[] selector = binaryMethod.isConstructor() ? type.getElementName().toCharArray() : binaryMethod.getSelector(); if (CharOperation.equals(selector, methodSelector)) { char[] signature = binaryMethod.getGenericSignature(); if (signature == null) signature = binaryMethod.getMethodDescriptor(); char[][] parameterTypes = Signature.getParameterTypes(signature); if (argCount != parameterTypes.length) continue nextMethod; if (argumentTypeNames != null) { for (int j = 0; j < argCount; j++) { char[] parameterTypeName = ClassFileMatchLocator.convertClassFileFormat(parameterTypes[j]); if (!CharOperation.endsWith(Signature.toCharArray(Signature.getTypeErasure(parameterTypeName)), CharOperation.replaceOnCopy(argumentTypeNames[j], '$', '.'))) continue nextMethod; parameterTypes[j] = parameterTypeName; } } return (IMethod) createMethodHandle(type, new String(selector), CharOperation.toStrings(parameterTypes)); } } } } return null; } /*
protected CompilationUnitDeclaration buildBindings(ICompilationUnit compilationUnit, boolean isTopLevelOrMember) throws JavaModelException { // source unit org.eclipse.jdt.internal.compiler.env.ICompilationUnit sourceUnit = (org.eclipse.jdt.internal.compiler.env.ICompilationUnit) compilationUnit; CompilationResult compilationResult = new CompilationResult(sourceUnit, 1, 1, 0); CompilationUnitDeclaration unit = isTopLevelOrMember ? this.locator.basicParser().dietParse(sourceUnit, compilationResult) : this.locator.basicParser().parse(sourceUnit, compilationResult); if (unit != null) { this.locator.lookupEnvironment.buildTypeBindings(unit, null /*no access restriction*/); this.locator.lookupEnvironment.completeTypeBindings(unit, !isTopLevelOrMember); if (!isTopLevelOrMember) { if (unit.scope != null) unit.scope.faultInTypes(); // fault in fields & methods unit.resolve(); } } return unit; } public char[][][] collect() throws JavaModelException {
indexMatches[j] = participant.getDocument(indexMatchPaths[j]); SearchDocument[] matches = MatchLocator.addWorkingCopies(pattern, indexMatches, getWorkingCopies(), participant); participant.locateMatches(matches, pattern, scope, requestor, monitor==null ? null : new SubProgressMonitor(monitor, 50));
private String getSourceFileName() { if (this.sourceFileName != null) return this.sourceFileName; this.sourceFileName = NO_SOURCE_FILE_NAME; if (this.openable.getSourceMapper() != null) { BinaryType type = (BinaryType) ((ClassFile) this.openable).getType(); ClassFileReader reader = MatchLocator.classFileReader(type); if (reader != null) { String fileName = type.sourceFileName(reader); this.sourceFileName = fileName == null ? NO_SOURCE_FILE_NAME : fileName; } } return this.sourceFileName; } boolean hasSimilarMatch() {
/** * Add additional source types */ public void accept(ISourceType[] sourceTypes, PackageBinding packageBinding, AccessRestriction accessRestriction) { // case of SearchableEnvironment of an IJavaProject is used ISourceType sourceType = sourceTypes[0]; while (sourceType.getEnclosingType() != null) sourceType = sourceType.getEnclosingType(); if (sourceType instanceof SourceTypeElementInfo) { // get source SourceTypeElementInfo elementInfo = (SourceTypeElementInfo) sourceType; IType type = elementInfo.getHandle(); ICompilationUnit sourceUnit = (ICompilationUnit) type.getCompilationUnit(); accept(sourceUnit, accessRestriction); } else { CompilationResult result = new CompilationResult(sourceType.getFileName(), 1, 1, 0); CompilationUnitDeclaration unit = SourceTypeConverter.buildCompilationUnit( sourceTypes, SourceTypeConverter.FIELD_AND_METHOD // need field and methods | SourceTypeConverter.MEMBER_TYPE, // need member types // no need for field initialization this.lookupEnvironment.problemReporter, result); this.lookupEnvironment.buildTypeBindings(unit, accessRestriction); this.lookupEnvironment.completeTypeBindings(unit, true); } } protected Parser basicParser() {
protected char[][][] computeSuperTypeNames(IType focusType) { String fullyQualifiedName = focusType.getFullyQualifiedName(); int lastDot = fullyQualifiedName.lastIndexOf('.'); char[] qualification = lastDot == -1 ? CharOperation.NO_CHAR : fullyQualifiedName.substring(0, lastDot).toCharArray(); char[] simpleName = focusType.getElementName().toCharArray(); SuperTypeNamesCollector superTypeNamesCollector = new SuperTypeNamesCollector( this.pattern, simpleName, qualification, new MatchLocator(this.pattern, this.requestor, this.scope, this.progressMonitor), // clone MatchLocator so that it has no side effect focusType, this.progressMonitor); try { this.allSuperTypeNames = superTypeNamesCollector.collect(); } catch (JavaModelException e) { // problem collecting super type names: leave it null } return this.allSuperTypeNames; } /**
IJavaElement enclosingElement = null; if (accuracy > -1) { enclosingElement = createHandle(field, type, parent); if (encloses(enclosingElement)) { int offset = field.sourceStart; SearchMatch match = newDeclarationMatch(enclosingElement, field.binding, accuracy, offset, field.sourceEnd-offset+1); if (field.initialization instanceof AllocationExpression) { reportAccurateEnumConstructorReference(match, field, (AllocationExpression) field.initialization); } else { report(match); enclosingElement = createHandle(field, type, parent); boolean report = (this.matchContainer & PatternLocator.FIELD_CONTAINER) != 0 && encloses(enclosingElement); MemberDeclarationVisitor declarationVisitor = new MemberDeclarationVisitor(enclosingElement, report ? nodes : null, nodeSet, this, typeInHierarchy); try { if (field.annotations != null) { if (enclosingElement == null) { enclosingElement = createHandle(field, type, parent); otherElements = createHandles(otherFields, type, parent); reportMatching(field.annotations, enclosingElement, otherElements, field.binding, nodeSet, true, true); } else { if (enclosingElement == null) enclosingElement = createHandle(field, type, parent); if (encloses(enclosingElement)) {
protected void reportDeclaration(MethodBinding methodBinding, MatchLocator locator, SimpleSet knownMethods) throws CoreException { ReferenceBinding declaringClass = methodBinding.declaringClass; IType type = locator.lookupType(declaringClass); if (type == null) return; // case of a secondary type method = locator.createBinaryMethodHandle(type, methodBinding.selector, parameterTypes); if (method == null || knownMethods.addIfNotIncluded(method) == null) return; if (resource == null) resource = type.getJavaProject().getProject(); IBinaryType info = locator.getBinaryInfo((org.eclipse.jdt.internal.core.ClassFile)type.getClassFile(), resource); locator.reportBinaryMemberDeclaration(resource, method, methodBinding, info, SearchMatch.A_ACCURATE); return; this.match = new MethodDeclarationMatch(method, SearchMatch.A_ACCURATE, offset, methodDecl.sourceEnd-offset+1, locator.getParticipant(), resource); locator.report(this.match);
enclosingElement = createHandle(lambdaExpression, parent); if (enclosingElement != null) { // skip if unable to find method if (encloses(enclosingElement)) { SearchMatch match = null; int length = lambdaExpression.arrowPosition() + 1 - nameSourceStart; match = this.patternLocator.newDeclarationMatch(lambdaExpression, enclosingElement, null, accuracy, length, this); if (match != null) { report(match); enclosingElement = createHandle(lambdaExpression, parent); boolean report = (this.matchContainer & PatternLocator.METHOD_CONTAINER) != 0 && encloses(enclosingElement); MemberDeclarationVisitor declarationVisitor = new MemberDeclarationVisitor(enclosingElement, report ? nodes : null, nodeSet, this, typeInHierarchy);
IBinaryType reader = classFileReader(type); if (reader != null) { IMethod binaryMethod = createBinaryMethodHandle(type, method.selector, argumentTypeNames); if (binaryMethod == null) { while (similarMatch != null) { type = ((ClassFile)similarMatch.openable).getType(); binaryMethod = createBinaryMethodHandle(type, method.selector, argumentTypeNames); if (binaryMethod != null) { return binaryMethod; return createMethodHandle(type, new String(method.selector), parameterTypeSignatures);
protected boolean createHierarchyResolver(IType focusType, PossibleMatch[] possibleMatches) { // cache focus type if not a possible match char[][] compoundName = CharOperation.splitOn('.', focusType.getFullyQualifiedName().toCharArray()); boolean isPossibleMatch = false; for (int i = 0, length = possibleMatches.length; i < length; i++) { if (CharOperation.equals(possibleMatches[i].compoundName, compoundName)) { isPossibleMatch = true; break; } } if (!isPossibleMatch) { if (focusType.isBinary()) { try { cacheBinaryType(focusType, null); } catch (JavaModelException e) { return false; } } else { // cache all types in the focus' compilation unit (even secondary types) accept((ICompilationUnit) focusType.getCompilationUnit(), null /*TODO no access restriction*/); } } // resolve focus type this.hierarchyResolver = new HierarchyResolver(this.lookupEnvironment, null/*hierarchy is not going to be computed*/); ReferenceBinding binding = this.hierarchyResolver.setFocusType(compoundName); return binding != null && binding.isValidBinding() && (binding.tagBits & TagBits.HierarchyHasProblems) == 0; } /**