| /******************************************************************************* |
| * Copyright (c) 2003 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Common Public License v0.5 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/cpl-v05.html |
| * |
| * Contributors: |
| * IBM Corp. - Rational Software - initial implementation |
| ******************************************************************************/ |
| /* |
| * Created on Jul 11, 2003 |
| */ |
| package org.eclipse.cdt.internal.core.search.matching; |
| |
| import java.io.IOException; |
| import java.util.Iterator; |
| |
| import org.eclipse.cdt.core.parser.ISourceElementCallbackDelegate; |
| import org.eclipse.cdt.core.parser.ast.IASTFunction; |
| import org.eclipse.cdt.core.parser.ast.IASTMethod; |
| import org.eclipse.cdt.core.parser.ast.IASTParameterDeclaration; |
| import org.eclipse.cdt.core.parser.ast.IASTQualifiedNameElement; |
| import org.eclipse.cdt.core.search.ICSearchScope; |
| import org.eclipse.cdt.internal.core.CharOperation; |
| import org.eclipse.cdt.internal.core.index.IEntryResult; |
| import org.eclipse.cdt.internal.core.index.impl.IndexInput; |
| import org.eclipse.cdt.internal.core.index.impl.IndexedFile; |
| import org.eclipse.cdt.internal.core.search.IIndexSearchRequestor; |
| import org.eclipse.cdt.internal.core.search.indexing.AbstractIndexer; |
| |
| /** |
| * @author aniefer |
| * |
| * To change the template for this generated type comment go to |
| * Window>Preferences>Java>Code Generation>Code and Comments |
| */ |
| public class MethodDeclarationPattern extends CSearchPattern { |
| |
| private SearchFor searchFor; |
| |
| private char[][] parameterNames; |
| private char[] simpleName; |
| private char[][] qualifications; |
| |
| private char[] decodedSimpleName; |
| private char[][] decodedQualifications; |
| |
| public MethodDeclarationPattern(char[] name, char[][] qual, char [][] params, int matchMode, SearchFor search, LimitTo limitTo, boolean caseSensitive) { |
| //super( name, params, matchMode, limitTo, caseSensitive ); |
| super( matchMode, caseSensitive, limitTo ); |
| |
| qualifications = qual; |
| simpleName = name; |
| parameterNames = params; |
| |
| searchFor = search; |
| } |
| |
| public char [] getSimpleName(){ |
| return simpleName; |
| } |
| |
| public int matchLevel(ISourceElementCallbackDelegate node, LimitTo limit ) { |
| if( node instanceof IASTMethod ){ |
| if( searchFor != METHOD || !canAccept( limit ) ){ |
| return IMPOSSIBLE_MATCH; |
| } |
| } else if ( node instanceof IASTFunction ){ |
| if( searchFor != FUNCTION || !canAccept( limit ) ){ |
| return IMPOSSIBLE_MATCH; |
| } |
| } else { |
| return IMPOSSIBLE_MATCH; |
| } |
| |
| IASTFunction function = (IASTFunction) node; |
| String nodeName = function.getName(); |
| |
| //check name, if simpleName == null, its treated the same as "*" |
| if( simpleName != null && !matchesName( simpleName, nodeName.toCharArray() ) ){ |
| return IMPOSSIBLE_MATCH; |
| } |
| |
| if( node instanceof IASTQualifiedNameElement ){ |
| //create char[][] out of full name, |
| String [] fullName = ((IASTQualifiedNameElement) node).getFullyQualifiedName(); |
| char [][] qualName = new char [ fullName.length - 1 ][]; |
| for( int i = 0; i < fullName.length - 1; i++ ){ |
| qualName[i] = fullName[i].toCharArray(); |
| } |
| |
| //check containing scopes |
| if( !matchQualifications( qualifications, qualName ) ){ |
| return IMPOSSIBLE_MATCH; |
| } |
| } |
| |
| //parameters |
| if( parameterNames != null && parameterNames.length > 0 && parameterNames[0].length > 0 ){ |
| |
| Iterator params = function.getParameters(); |
| |
| for( int i = 0; i < parameterNames.length; i++ ){ |
| |
| //if this function doesn't have this many parameters, it is not a match. |
| //or if this function has a parameter, but parameterNames only has null. |
| if( !params.hasNext() || parameterNames[ i ] == null ) |
| return IMPOSSIBLE_MATCH; |
| |
| IASTParameterDeclaration parameter = (IASTParameterDeclaration) params.next(); |
| char[] param = CSearchPattern.getParamString( parameter ); |
| |
| //no wildcards in parameters strings |
| if( !CharOperation.equals( parameterNames[i], param, _caseSensitive ) ) |
| return IMPOSSIBLE_MATCH; |
| } |
| |
| //if this function still has more parameters, it is not a match |
| if( params.hasNext() ) |
| return IMPOSSIBLE_MATCH; |
| } |
| |
| return ACCURATE_MATCH; |
| } |
| |
| public char[] indexEntryPrefix() { |
| if( searchFor == FUNCTION ) |
| return AbstractIndexer.bestFunctionPrefix( _limitTo, simpleName, _matchMode, _caseSensitive ); |
| else if( searchFor == METHOD ) |
| return AbstractIndexer.bestMethodPrefix( _limitTo, simpleName, qualifications, _matchMode, _caseSensitive ); |
| else return null; |
| } |
| |
| protected void resetIndexInfo(){ |
| decodedSimpleName = null; |
| decodedQualifications = null; |
| } |
| |
| protected void decodeIndexEntry(IEntryResult entryResult) { |
| char[] word = entryResult.getWord(); |
| int size = word.length; |
| |
| int firstSlash = CharOperation.indexOf( SEPARATOR, word, 0 ); |
| |
| int slash = CharOperation.indexOf( SEPARATOR, word, firstSlash + 1 ); |
| |
| this.decodedSimpleName = CharOperation.subarray(word, firstSlash + 1, slash); |
| |
| if( slash != -1 && slash+1 < size ){ |
| char [][] temp = CharOperation.splitOn('/', CharOperation.subarray(word, slash + 1, size)); |
| this.decodedQualifications = new char [ temp.length ][]; |
| for( int i = 0; i < temp.length; i++ ){ |
| this.decodedQualifications[ i ] = temp[ temp.length - i - 1 ]; |
| } |
| } |
| } |
| |
| protected boolean matchIndexEntry() { |
| /* check simple name matches */ |
| if (simpleName != null){ |
| if( ! matchesName( simpleName, decodedSimpleName ) ){ |
| return false; |
| } |
| } |
| |
| if( !matchQualifications( qualifications, decodedQualifications ) ){ |
| return false; |
| } |
| |
| return true; |
| } |
| |
| public void feedIndexRequestor(IIndexSearchRequestor requestor, int detailLevel, int[] references, IndexInput input, ICSearchScope scope) throws IOException { |
| for (int i = 0, max = references.length; i < max; i++) { |
| IndexedFile file = input.getIndexedFile(references[i]); |
| String path; |
| if (file != null && scope.encloses(path =file.getPath())) { |
| if( searchFor == METHOD ) |
| requestor.acceptMethodDeclaration(path, decodedSimpleName, parameterNames.length, decodedQualifications); |
| else if ( searchFor == FUNCTION ) |
| requestor.acceptFunctionDeclaration(path, decodedSimpleName, parameterNames.length); |
| } |
| } |
| } |
| } |