mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-08-05 07:15:39 +02:00
Patch from Devin Steffler: getDeclarations
This commit is contained in:
parent
a36a7f8613
commit
4dcca4a96a
5 changed files with 834 additions and 69 deletions
File diff suppressed because it is too large
Load diff
|
@ -44,7 +44,7 @@ public interface IASTTranslationUnit extends IASTNode {
|
||||||
* @param binding
|
* @param binding
|
||||||
* @return List of IASTName nodes for the binding's declaration
|
* @return List of IASTName nodes for the binding's declaration
|
||||||
*/
|
*/
|
||||||
public IASTDeclaration[] getDeclarations(IBinding binding);
|
public IASTName[] getDeclarations(IBinding binding);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the list of references in this translation unit to the given
|
* Returns the list of references in this translation unit to the given
|
||||||
|
|
|
@ -99,9 +99,8 @@ public class CASTTranslationUnit extends CASTNode implements IASTTranslationUnit
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
* @see org.eclipse.cdt.core.dom.ast.IASTTranslationUnit#getDeclarations(org.eclipse.cdt.core.dom.ast.IBinding)
|
* @see org.eclipse.cdt.core.dom.ast.IASTTranslationUnit#getDeclarations(org.eclipse.cdt.core.dom.ast.IBinding)
|
||||||
*/
|
*/
|
||||||
public IASTDeclaration[] getDeclarations(IBinding binding) {
|
public IASTName[] getDeclarations(IBinding binding) {
|
||||||
// TODO Auto-generated method stub
|
return CVisitor.getDeclarations(this, binding);
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
|
|
|
@ -45,12 +45,14 @@ import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTInitializerList;
|
import org.eclipse.cdt.core.dom.ast.IASTInitializerList;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTLabelStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTLabelStatement;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTName;
|
import org.eclipse.cdt.core.dom.ast.IASTName;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.IASTNamedTypeSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTNode;
|
import org.eclipse.cdt.core.dom.ast.IASTNode;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
|
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
|
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTProblem;
|
import org.eclipse.cdt.core.dom.ast.IASTProblem;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTProblemHolder;
|
import org.eclipse.cdt.core.dom.ast.IASTProblemHolder;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTReturnStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTReturnStatement;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
|
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTStatement;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTSwitchStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTSwitchStatement;
|
||||||
|
@ -75,6 +77,7 @@ import org.eclipse.cdt.core.dom.ast.c.ICASTCompositeTypeSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTDeclSpecifier;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTDeclSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTElaboratedTypeSpecifier;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTElaboratedTypeSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTEnumerationSpecifier;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTEnumerationSpecifier;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.c.ICASTFieldDesignator;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTPointer;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTPointer;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTSimpleDeclSpecifier;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTSimpleDeclSpecifier;
|
||||||
import org.eclipse.cdt.core.dom.ast.c.ICASTTypeIdInitializerExpression;
|
import org.eclipse.cdt.core.dom.ast.c.ICASTTypeIdInitializerExpression;
|
||||||
|
@ -227,6 +230,146 @@ public class CVisitor {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static class CollectDeclarationsAction extends CBaseVisitorAction {
|
||||||
|
{
|
||||||
|
processDeclarators = true;
|
||||||
|
processDeclSpecifiers = true;
|
||||||
|
processEnumerators = true;
|
||||||
|
processStatements = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final int DEFAULT_CHILDREN_LIST_SIZE = 8;
|
||||||
|
private IASTName[] declsFound = null;
|
||||||
|
int numFound = 0;
|
||||||
|
IBinding binding = null;
|
||||||
|
boolean functionDeclared = false;
|
||||||
|
boolean compositeTypeDeclared = false;
|
||||||
|
|
||||||
|
private void addName(IASTName name) {
|
||||||
|
if( declsFound.length == numFound ) // if the found array is full, then double the array
|
||||||
|
{
|
||||||
|
IASTName [] old = declsFound;
|
||||||
|
declsFound = new IASTName[ old.length * 2 ];
|
||||||
|
for( int j = 0; j < old.length; ++j )
|
||||||
|
declsFound[j] = old[j];
|
||||||
|
}
|
||||||
|
declsFound[numFound++] = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
private IASTName[] removeNullFromNames() {
|
||||||
|
if (declsFound[declsFound.length-1] != null) { // if the last element in the list is not null then return the list
|
||||||
|
return declsFound;
|
||||||
|
} else if (declsFound[0] == null) { // if the first element in the list is null, then return empty list
|
||||||
|
return new IASTName[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
IASTName[] results = new IASTName[numFound];
|
||||||
|
for (int i=0; i<results.length; i++)
|
||||||
|
results[i] = declsFound[i];
|
||||||
|
|
||||||
|
return results;
|
||||||
|
}
|
||||||
|
|
||||||
|
public IASTName[] getDeclarationNames() {
|
||||||
|
return removeNullFromNames();
|
||||||
|
}
|
||||||
|
|
||||||
|
public CollectDeclarationsAction(IBinding binding) {
|
||||||
|
declsFound = new IASTName[DEFAULT_CHILDREN_LIST_SIZE];
|
||||||
|
this.binding = binding;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.eclipse.cdt.internal.core.dom.parser.c.CVisitor.CBaseVisitorAction#processDeclarator(org.eclipse.cdt.core.dom.ast.IASTDeclarator)
|
||||||
|
*/
|
||||||
|
public boolean processDeclarator(IASTDeclarator declarator) {
|
||||||
|
if ( declarator == null ) return true;
|
||||||
|
|
||||||
|
IASTNode parent = declarator.getParent();
|
||||||
|
while (parent != null && !(parent instanceof IASTDeclaration))
|
||||||
|
parent = parent.getParent();
|
||||||
|
|
||||||
|
if ( parent instanceof IASTDeclaration ) {
|
||||||
|
if ( !functionDeclared && parent != null && parent instanceof IASTFunctionDefinition ) {
|
||||||
|
if ( declarator.getName() != null && declarator.getName().resolveBinding() == binding ) {
|
||||||
|
functionDeclared = true;
|
||||||
|
addName(declarator.getName());
|
||||||
|
}
|
||||||
|
} else if ( parent instanceof IASTSimpleDeclaration ) {
|
||||||
|
if ( (declarator.getName() != null && declarator.getName().resolveBinding() == binding) ) {
|
||||||
|
if ( declarator instanceof IASTFunctionDeclarator ) {
|
||||||
|
functionDeclared = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
addName(declarator.getName());
|
||||||
|
}
|
||||||
|
} else if ( parent instanceof IASTParameterDeclaration ) {
|
||||||
|
if ( declarator.getName() != null && declarator.getName().resolveBinding() == binding ) {
|
||||||
|
addName(declarator.getName());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.eclipse.cdt.internal.core.dom.parser.c.CVisitor.CBaseVisitorAction#processDeclSpecifier(org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier)
|
||||||
|
*/
|
||||||
|
public boolean processDeclSpecifier(IASTDeclSpecifier declSpec) {
|
||||||
|
if ( declSpec instanceof IASTSimpleDeclSpecifier ||
|
||||||
|
declSpec instanceof ICASTTypedefNameSpecifier ) return true;
|
||||||
|
|
||||||
|
if ( !compositeTypeDeclared && declSpec != null && declSpec instanceof IASTCompositeTypeSpecifier ) {
|
||||||
|
if (((IASTCompositeTypeSpecifier)declSpec).getName().resolveBinding() == binding) {
|
||||||
|
compositeTypeDeclared = true;
|
||||||
|
addName(((IASTCompositeTypeSpecifier)declSpec).getName());
|
||||||
|
}
|
||||||
|
} else if (!compositeTypeDeclared && declSpec instanceof IASTElaboratedTypeSpecifier ) {
|
||||||
|
if (((IASTElaboratedTypeSpecifier)declSpec).getName().resolveBinding() == binding) {
|
||||||
|
compositeTypeDeclared = true;
|
||||||
|
addName(((IASTElaboratedTypeSpecifier)declSpec).getName());
|
||||||
|
}
|
||||||
|
} else if (!compositeTypeDeclared && declSpec instanceof IASTEnumerationSpecifier ) {
|
||||||
|
if (((IASTEnumerationSpecifier)declSpec).getName().resolveBinding() == binding) {
|
||||||
|
compositeTypeDeclared = true;
|
||||||
|
addName(((IASTEnumerationSpecifier)declSpec).getName());
|
||||||
|
}
|
||||||
|
} else if ( declSpec instanceof IASTNamedTypeSpecifier ) {
|
||||||
|
if (((IASTNamedTypeSpecifier)declSpec).getName().resolveBinding() == binding)
|
||||||
|
addName(((IASTNamedTypeSpecifier)declSpec).getName());
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.eclipse.cdt.internal.core.dom.parser.c.CVisitor.CBaseVisitorAction#processEnumerator(org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator)
|
||||||
|
*/
|
||||||
|
public boolean processEnumerator(IASTEnumerator enumerator) {
|
||||||
|
if (enumerator.getName().resolveBinding() == binding) {
|
||||||
|
IASTNode parent = enumerator.getParent();
|
||||||
|
while (parent != null && !(parent instanceof IASTDeclaration))
|
||||||
|
parent = parent.getParent();
|
||||||
|
|
||||||
|
if (parent != null && parent instanceof IASTDeclaration) addName(enumerator.getName());
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.eclipse.cdt.internal.core.dom.parser.c.CVisitor.CBaseVisitorAction#processStatement(org.eclipse.cdt.core.dom.ast.IASTStatement)
|
||||||
|
*/
|
||||||
|
public boolean processStatement(IASTStatement statement) {
|
||||||
|
if ( statement instanceof IASTLabelStatement )
|
||||||
|
if ( ((IASTLabelStatement)statement).getName().resolveBinding() == binding )
|
||||||
|
addName(((IASTLabelStatement)statement).getName());
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//lookup bits
|
//lookup bits
|
||||||
private static final int COMPLETE = 0;
|
private static final int COMPLETE = 0;
|
||||||
private static final int CURRENT_SCOPE = 1;
|
private static final int CURRENT_SCOPE = 1;
|
||||||
|
@ -258,6 +401,8 @@ public class CVisitor {
|
||||||
binding = createBinding( (ICASTEnumerationSpecifier) parent );
|
binding = createBinding( (ICASTEnumerationSpecifier) parent );
|
||||||
} else if( parent instanceof IASTEnumerator ) {
|
} else if( parent instanceof IASTEnumerator ) {
|
||||||
binding = createBinding( (IASTEnumerator) parent );
|
binding = createBinding( (IASTEnumerator) parent );
|
||||||
|
} else if( parent instanceof ICASTFieldDesignator ) {
|
||||||
|
binding = resolveBinding( parent );
|
||||||
}
|
}
|
||||||
((CASTName)name).setBinding( binding );
|
((CASTName)name).setBinding( binding );
|
||||||
}
|
}
|
||||||
|
@ -493,6 +638,8 @@ public class CVisitor {
|
||||||
} else if( node instanceof IASTParameterDeclaration ){
|
} else if( node instanceof IASTParameterDeclaration ){
|
||||||
IASTParameterDeclaration param = (IASTParameterDeclaration) node;
|
IASTParameterDeclaration param = (IASTParameterDeclaration) node;
|
||||||
IASTFunctionDeclarator fDtor = (IASTFunctionDeclarator) param.getParent();
|
IASTFunctionDeclarator fDtor = (IASTFunctionDeclarator) param.getParent();
|
||||||
|
|
||||||
|
if ( fDtor.getName().resolveBinding() instanceof IFunction ) { // possible to have IASTParameterDeclaration whose parent is an IVariable
|
||||||
IFunction function = (IFunction) fDtor.getName().resolveBinding();
|
IFunction function = (IFunction) fDtor.getName().resolveBinding();
|
||||||
if( function.getPhysicalNode() != fDtor ) {
|
if( function.getPhysicalNode() != fDtor ) {
|
||||||
IASTParameterDeclaration [] ps = fDtor.getParameters();
|
IASTParameterDeclaration [] ps = fDtor.getParameters();
|
||||||
|
@ -504,6 +651,7 @@ public class CVisitor {
|
||||||
return (IBinding) params.get( index );
|
return (IBinding) params.get( index );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} else if( node instanceof IASTTypeId ){
|
} else if( node instanceof IASTTypeId ){
|
||||||
IASTTypeId typeId = (IASTTypeId) node;
|
IASTTypeId typeId = (IASTTypeId) node;
|
||||||
IASTDeclSpecifier declSpec = typeId.getDeclSpecifier();
|
IASTDeclSpecifier declSpec = typeId.getDeclSpecifier();
|
||||||
|
@ -516,6 +664,36 @@ public class CVisitor {
|
||||||
if( name != null ){
|
if( name != null ){
|
||||||
return name.resolveBinding();
|
return name.resolveBinding();
|
||||||
}
|
}
|
||||||
|
} else if( node instanceof ICASTFieldDesignator ) {
|
||||||
|
IASTNode blockItem = getContainingBlockItem( node );
|
||||||
|
|
||||||
|
IASTNode parent = node.getParent();
|
||||||
|
while ( parent != null && !(parent.getParent() instanceof IASTTranslationUnit) )
|
||||||
|
parent = parent.getParent();
|
||||||
|
|
||||||
|
if ( parent.getParent() instanceof IASTTranslationUnit &&
|
||||||
|
blockItem instanceof IASTDeclarationStatement &&
|
||||||
|
((IASTDeclarationStatement)blockItem).getDeclaration() instanceof IASTSimpleDeclaration &&
|
||||||
|
((IASTSimpleDeclaration)((IASTDeclarationStatement)blockItem).getDeclaration()).getDeclSpecifier() instanceof IASTNamedTypeSpecifier ) {
|
||||||
|
// TODO use getDefinitions below instead of getDeclarations (i.e. want collection of defined members and the declaration doesn't always have it)
|
||||||
|
IASTName declNames[] = ((IASTTranslationUnit)parent.getParent()).getDeclarations(((IASTNamedTypeSpecifier)((IASTSimpleDeclaration)((IASTDeclarationStatement)blockItem).getDeclaration()).getDeclSpecifier()).getName().resolveBinding());
|
||||||
|
for (int i=0; i<declNames.length; i++) {
|
||||||
|
IASTNode declBlockItem = getContainingBlockItem(declNames[i]);
|
||||||
|
if ( declBlockItem instanceof IASTSimpleDeclaration ) {
|
||||||
|
if (((IASTSimpleDeclaration)declBlockItem).getDeclSpecifier() instanceof IASTCompositeTypeSpecifier ) {
|
||||||
|
IASTDeclaration[] decls = ((IASTCompositeTypeSpecifier)((IASTSimpleDeclaration)declBlockItem).getDeclSpecifier()).getMembers();
|
||||||
|
for (int j=0; j<decls.length; j++) {
|
||||||
|
if (decls[j] instanceof IASTSimpleDeclaration) {
|
||||||
|
IASTDeclarator[] decltors = ((IASTSimpleDeclaration)decls[j]).getDeclarators();
|
||||||
|
for(int k=0; k<decltors.length; k++)
|
||||||
|
if (CharArrayUtils.equals(decltors[k].getName().toCharArray(), ((ICASTFieldDesignator)node).getName().toCharArray()))
|
||||||
|
return decltors[k].getName().resolveBinding();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
@ -1351,4 +1529,11 @@ public class CVisitor {
|
||||||
|
|
||||||
return action.getProblems();
|
return action.getProblems();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static IASTName[] getDeclarations(IASTTranslationUnit tu, IBinding binding) {
|
||||||
|
CollectDeclarationsAction action = new CollectDeclarationsAction(binding);
|
||||||
|
visitTranslationUnit(tu, action);
|
||||||
|
|
||||||
|
return action.getDeclarationNames();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -116,7 +116,7 @@ public class CPPASTTranslationUnit extends CPPASTNode implements
|
||||||
*
|
*
|
||||||
* @see org.eclipse.cdt.core.dom.ast.IASTTranslationUnit#getDeclarations(org.eclipse.cdt.core.dom.ast.IBinding)
|
* @see org.eclipse.cdt.core.dom.ast.IASTTranslationUnit#getDeclarations(org.eclipse.cdt.core.dom.ast.IBinding)
|
||||||
*/
|
*/
|
||||||
public IASTDeclaration[] getDeclarations(IBinding b) {
|
public IASTName[] getDeclarations(IBinding b) {
|
||||||
// TODO Auto-generated method stub
|
// TODO Auto-generated method stub
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue