From 30322c916c320af81c7feba95ae4765903ccf193 Mon Sep 17 00:00:00 2001 From: Anton Leherbauer Date: Wed, 18 Apr 2007 10:43:39 +0000 Subject: [PATCH] Fix for 182294: Open Type should allow to open functions and variables --- .../cdt/core/browser/IFunctionInfo.java | 34 +++++++++ .../cdt/core/browser/IndexTypeInfo.java | 62 ++++++++++++++-- .../core/browser/IndexTypeReference.java | 74 +++++++++++++++++++ .../core/browser/util/IndexModelUtil.java | 56 +++++++++++++- 4 files changed, 217 insertions(+), 9 deletions(-) create mode 100644 core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IFunctionInfo.java create mode 100644 core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/IndexTypeReference.java diff --git a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IFunctionInfo.java b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IFunctionInfo.java new file mode 100644 index 00000000000..ca900fed035 --- /dev/null +++ b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IFunctionInfo.java @@ -0,0 +1,34 @@ +/******************************************************************************* + * Copyright (c) 2007 Wind River Systems, Inc. and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Anton Leherbauer (Wind River Systems) - initial API and implementation + *******************************************************************************/ + +package org.eclipse.cdt.core.browser; + +/** + * Provide function related information. + * + *

+ * Not intended to be implemented by clients. + *

+ * + * @since 4.0 + */ +public interface IFunctionInfo { + + /** + * @return the function parameter types + */ + public String[] getParameters(); + /** + * @return the function return type + */ + public String getReturnType(); + +} diff --git a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IndexTypeInfo.java b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IndexTypeInfo.java index 96b9f26867f..ccb97656a59 100644 --- a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IndexTypeInfo.java +++ b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/core/browser/IndexTypeInfo.java @@ -9,18 +9,25 @@ * QNX - Initial API and implementation * IBM Corporation * Andrew Ferguson (Symbian) + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.core.browser; +import java.util.Arrays; + import org.eclipse.cdt.core.CCorePlugin; +import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.IBinding; +import org.eclipse.cdt.core.dom.ast.IFunction; import org.eclipse.cdt.core.index.IIndex; import org.eclipse.cdt.core.index.IIndexBinding; import org.eclipse.cdt.core.index.IIndexFileLocation; import org.eclipse.cdt.core.index.IIndexName; import org.eclipse.cdt.core.index.IndexFilter; +import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; import org.eclipse.cdt.core.parser.ast.ASTAccessVisibility; +import org.eclipse.cdt.internal.core.browser.IndexTypeReference; import org.eclipse.cdt.internal.core.browser.util.IndexModelUtil; import org.eclipse.cdt.internal.core.pdom.dom.PDOMNotImplementedError; import org.eclipse.core.filesystem.URIUtil; @@ -36,16 +43,28 @@ import org.eclipse.core.runtime.Path; * @author Doug Schaefer * */ -public class IndexTypeInfo implements ITypeInfo { +public class IndexTypeInfo implements ITypeInfo, IFunctionInfo { private final String[] fqn; private final int elementType; private final IIndex index; + private final String[] params; + private final String returnType; private ITypeReference reference; // lazily constructed public IndexTypeInfo(String[] fqn, int elementType, IIndex index) { this.fqn = fqn; this.elementType = elementType; this.index = index; + this.params= null; + this.returnType= null; + } + + public IndexTypeInfo(String[] fqn, int elementType, String[] params, String returnType, IIndex index) { + this.fqn = fqn; + this.elementType = elementType; + this.params= params; + this.returnType= returnType; + this.index = index; } public void addDerivedReference(ITypeReference location) { @@ -130,26 +149,41 @@ public class IndexTypeInfo implements ITypeInfo { IIndexBinding[] ibs = index.findBindings(cfqn, new IndexFilter() { public boolean acceptBinding(IBinding binding) { - return IndexModelUtil.bindingHasCElementType(binding, new int[]{elementType}); + boolean sameType= IndexModelUtil.bindingHasCElementType(binding, new int[]{elementType}); + if (sameType && binding instanceof IFunction && params != null) { + String[] otherParams; + try { + otherParams= IndexModelUtil.extractParameterTypes((IFunction)binding); + return Arrays.equals(params, otherParams); + } catch (DOMException exc) { + CCorePlugin.log(exc); + } + } + return sameType; } }, new NullProgressMonitor()); if(ibs.length>0) { - IIndexName[] names = index.findNames(ibs[0], IIndex.FIND_DEFINITIONS); + IIndexName[] names; + if (elementType == ICElement.C_TYPEDEF) { + names= index.findNames(ibs[0], IIndex.FIND_DECLARATIONS); + } else { + names= index.findNames(ibs[0], IIndex.FIND_DEFINITIONS); + } if(names.length>0) { IIndexFileLocation ifl = names[0].getFile().getLocation(); String fullPath = ifl.getFullPath(); if(fullPath!=null) { IFile file = ResourcesPlugin.getWorkspace().getRoot().getFile(new Path(fullPath)); if(file!=null) { - reference = new TypeReference( - file, file.getProject(), names[0].getNodeOffset(), names[0].getNodeLength() + reference = new IndexTypeReference( + ibs[0], file, file.getProject(), names[0].getNodeOffset(), names[0].getNodeLength() ); } } else { IPath path = URIUtil.toPath(ifl.getURI()); if(path!=null) { - reference = new TypeReference( - path, null, names[0].getNodeOffset(), names[0].getNodeLength() + reference = new IndexTypeReference( + ibs[0], path, null, names[0].getNodeOffset(), names[0].getNodeLength() ); } } @@ -230,4 +264,18 @@ public class IndexTypeInfo implements ITypeInfo { throw new PDOMNotImplementedError(); } + /* + * @see org.eclipse.cdt.internal.core.browser.IFunctionInfo#getParameters() + */ + public String[] getParameters() { + return params; + } + + /* + * @see org.eclipse.cdt.internal.core.browser.IFunctionInfo#getReturnType() + */ + public String getReturnType() { + return returnType; + } + } diff --git a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/IndexTypeReference.java b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/IndexTypeReference.java new file mode 100644 index 00000000000..327ceb83b91 --- /dev/null +++ b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/IndexTypeReference.java @@ -0,0 +1,74 @@ +/******************************************************************************* + * Copyright (c) 2007 Wind River Systems, Inc. and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Anton Leherbauer (Wind River Systems) - initial API and implementation + *******************************************************************************/ + +package org.eclipse.cdt.internal.core.browser; + +import org.eclipse.cdt.core.browser.TypeReference; +import org.eclipse.cdt.core.dom.ast.DOMException; +import org.eclipse.cdt.core.dom.ast.IBinding; +import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.core.model.ITranslationUnit; +import org.eclipse.cdt.internal.core.model.ext.CElementHandleFactory; +import org.eclipse.core.resources.IProject; +import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.CoreException; +import org.eclipse.core.runtime.IPath; +import org.eclipse.jface.text.IRegion; +import org.eclipse.jface.text.Region; + +/** + * A {@link IndexTypeReference} tailored for index bindings. + * + * @since 4.0 + */ +public class IndexTypeReference extends TypeReference { + + private ICElement fCElement; + + public IndexTypeReference(IBinding binding, IPath path, IProject project, int offset, int length) { + super(path, project, offset, length); + fCElement= createCElement(binding); + } + + public IndexTypeReference(IBinding binding, IResource resource, IProject project, int offset, int length) { + super(resource, project, offset, length); + fCElement= createCElement(binding); + } + + /** + * Compute the C element handle for the given binding. + * @param binding + */ + private ICElement createCElement(IBinding binding) { + ITranslationUnit tu= getTranslationUnit(); + if (tu != null) { + long timestamp= tu.getResource() != null ? tu.getResource().getLocalTimeStamp() : 0; + IRegion region= new Region(getOffset(), getLength()); + try { + return CElementHandleFactory.create(tu, binding, region, timestamp); + } catch (CoreException exc) { + } catch (DOMException exc) { + } + } + return null; + } + + /* + * @see org.eclipse.cdt.core.browser.ITypeReference#getCElements() + */ + public ICElement[] getCElements() { + if (fCElement != null) { + return new ICElement[] { fCElement }; + } + return super.getCElements(); + } + +} diff --git a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/util/IndexModelUtil.java b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/util/IndexModelUtil.java index b0e14ea7d08..faed1859837 100644 --- a/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/util/IndexModelUtil.java +++ b/core/org.eclipse.cdt.core/browser/org/eclipse/cdt/internal/core/browser/util/IndexModelUtil.java @@ -9,15 +9,20 @@ * QNX - Initial API and implementation * IBM Corporation * Andrew Ferguson (Symbian) + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.browser.util; import org.eclipse.cdt.core.CCorePlugin; +import org.eclipse.cdt.core.dom.ast.ASTTypeUtil; import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.ICompositeType; import org.eclipse.cdt.core.dom.ast.IEnumeration; +import org.eclipse.cdt.core.dom.ast.IFunction; +import org.eclipse.cdt.core.dom.ast.IParameter; import org.eclipse.cdt.core.dom.ast.ITypedef; +import org.eclipse.cdt.core.dom.ast.IVariable; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceAlias; @@ -29,6 +34,8 @@ import org.eclipse.cdt.core.model.ICElement; * This is internal in case some IBinding's do not have ICElement constants in future */ public class IndexModelUtil { + private static final String[] EMPTY_STRING_ARRAY= {}; + /** * Returns whether the binding is of any of the specified CElement type constants * @param binding @@ -66,6 +73,14 @@ public class IndexModelUtil { if(binding instanceof ITypedef) return true; break; + case ICElement.C_FUNCTION: + if(binding instanceof IFunction) + return true; + break; + case ICElement.C_VARIABLE: + if(binding instanceof IVariable) + return true; + break; } } } catch(DOMException de) { @@ -100,10 +115,47 @@ public class IndexModelUtil { if (binding instanceof ICPPNamespace || binding instanceof ICPPNamespaceAlias) { elementType = ICElement.C_NAMESPACE; } - if (binding instanceof IEnumeration) { - elementType = ICElement.C_ENUMERATION; + elementType = ICElement.C_ENUMERATION; + } + if (binding instanceof ITypedef) { + elementType = ICElement.C_TYPEDEF; + } + if (binding instanceof IFunction) { + elementType = ICElement.C_FUNCTION; + } + if (binding instanceof IVariable) { + elementType = ICElement.C_VARIABLE; } return elementType; } + + /** + * Extract the parmaeter types of the given function as array of strings. + * @param function + * @return the parameter types of the function + * @throws DOMException + */ + public static String[] extractParameterTypes(IFunction function) throws DOMException { + IParameter[] params= function.getParameters(); + String[] parameterTypes= new String[params.length]; + for (int i = 0; i < params.length; i++) { + IParameter param = params[i]; + parameterTypes[i]= ASTTypeUtil.getType(param.getType()); + } + if (parameterTypes.length == 1 && parameterTypes[0].equals("void")) { //$NON-NLS-1$ + return EMPTY_STRING_ARRAY; + } + return parameterTypes; + } + + /** + * Extract the return type of the given function as string. + * @param function + * @return the return type of the function + * @throws DOMException + */ + public static String extractReturnType(IFunction function) throws DOMException { + return ASTTypeUtil.getType(function.getType().getReturnType()); + } }