1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-07-25 01:45:33 +02:00

214646: apply fix

This commit is contained in:
Andrew Ferguson 2008-01-15 13:38:10 +00:00
parent 1bd375a30e
commit 8a24d5717e
9 changed files with 962 additions and 1091 deletions

View file

@ -9,6 +9,7 @@
* IBM - Initial API and implementation
* Markus Schorn (Wind River Systems)
* Bryan Wilkinson (QNX)
* Andrew Ferguson (Symbian)
*******************************************************************************/
/*
* Created on Mar 11, 2005
@ -52,6 +53,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionTemplate;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateNonTypeParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
@ -2142,4 +2144,42 @@ public class AST2TemplateTests extends AST2BaseTest {
}
}
}
// class A {};
//
// template <class T> class C {
// public:
// inline C(T& aRef) {}
// inline operator T&() {}
// };
//
// void foo(A a) {}
// void bar(C<const A> ca) {}
//
// void main2() {
// const A a= *new A();
// const C<const A> ca= *new C<const A>(*new A());
//
// foo(a);
// bar(ca);
// }
public void testBug214646() throws Exception {
BindingAssertionHelper bh= new BindingAssertionHelper(getContents(1)[0].toString(), true);
IBinding b0= bh.assertNonProblem("foo(a)", 3);
IBinding b1= bh.assertNonProblem("bar(ca)", 3);
assertInstance(b0, ICPPFunction.class);
assertInstance(b1, ICPPFunction.class);
ICPPFunction f0= (ICPPFunction) b0, f1= (ICPPFunction) b1;
assertEquals(1, f0.getParameters().length);
assertEquals(1, f1.getParameters().length);
assertInstance(f0.getParameters()[0].getType(), ICPPClassType.class);
assertFalse(f0 instanceof ICPPTemplateInstance);
assertFalse(f0 instanceof ICPPTemplateDefinition);
assertInstance(f1.getParameters()[0].getType(), ICPPClassType.class);
assertInstance(f1.getParameters()[0].getType(), ICPPTemplateInstance.class);
}
}

View file

@ -8,10 +8,8 @@
* Contributors:
* IBM - Initial API and implementation
* Bryan Wilkinson (QNX)
* Andrew Ferguson (Symbian)
*******************************************************************************/
/*
* Created on Mar 28, 2005
*/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException;
@ -32,14 +30,15 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.ObjectMap;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.index.IIndexType;
/**
* @author aniefer
*/
public class CPPClassInstance extends CPPInstance implements ICPPClassType, ICPPInternalBinding {
public class CPPClassInstance extends CPPInstance implements ICPPClassType, ICPPInternalClassType {
private CPPClassSpecializationScope instanceScope;
/**
* @param decl
* @param args
@ -59,15 +58,15 @@ public class CPPClassInstance extends CPPInstance implements ICPPClassType, ICPP
ICPPBase [] bindings = cls.getBases();
for (int i = 0; i < bindings.length; i++) {
ICPPBase specBinding = (ICPPBase) ((ICPPInternalBase)bindings[i]).clone();
IBinding base = bindings[i].getBaseClass();
if (base instanceof IType) {
IType specBase = CPPTemplates.instantiateType((IType) base, argumentMap);
specBase = CPPSemantics.getUltimateType(specBase, false);
if (specBase instanceof IBinding) {
((ICPPInternalBase)specBinding).setBaseClass((IBinding)specBase);
}
result = (ICPPBase[]) ArrayUtil.append(ICPPBase.class, result, specBinding);
}
IBinding base = bindings[i].getBaseClass();
if (base instanceof IType) {
IType specBase = CPPTemplates.instantiateType((IType) base, argumentMap);
specBase = CPPSemantics.getUltimateType(specBase, false);
if (specBase instanceof IBinding) {
((ICPPInternalBase)specBinding).setBaseClass((IBinding)specBase);
}
result = (ICPPBase[]) ArrayUtil.append(ICPPBase.class, result, specBinding);
}
}
return (ICPPBase[]) ArrayUtil.trim(ICPPBase.class, result);
}
@ -172,42 +171,51 @@ public class CPPClassInstance extends CPPInstance implements ICPPClassType, ICPP
return new CPPClassType.CPPClassTypeDelegate( name, this );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.IType#isSameType(org.eclipse.cdt.core.dom.ast.IType)
*/
public boolean isSameType( IType type ) {
if( type == this )
return true;
if( type instanceof ITypedef || type instanceof IIndexType )
return type.isSameType( this );
if( type instanceof ICPPDeferredTemplateInstance && type instanceof ICPPClassType )
return type.isSameType( this ); //the CPPDeferredClassInstance has some fuzziness
if( type instanceof ICPPTemplateInstance ){
ICPPClassType ct1= (ICPPClassType) getSpecializedBinding();
ICPPClassType ct2= (ICPPClassType) ((ICPPTemplateInstance)type).getTemplateDefinition();
if(!ct1.isSameType(ct2))
return false;
ObjectMap m1 = getArgumentMap(), m2 = ((ICPPTemplateInstance)type).getArgumentMap();
if( m1 == null || m2 == null || m1.size() != m2.size())
return false;
for( int i = 0; i < m1.size(); i++ ){
IType t1 = (IType) m1.getAt( i );
IType t2 = (IType) m2.getAt( i );
if( t1 == null || ! t1.isSameType( t2 ) )
return false;
}
return true;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.IType#isSameType(org.eclipse.cdt.core.dom.ast.IType)
*/
public boolean isSameType( IType type ) {
if( type == this )
return true;
if( type instanceof ITypedef || type instanceof IIndexType )
return type.isSameType( this );
if( type instanceof ICPPDeferredTemplateInstance && type instanceof ICPPClassType )
return type.isSameType( this ); //the CPPDeferredClassInstance has some fuzziness
return false;
}
if( type instanceof ICPPTemplateInstance ){
ICPPClassType ct1= (ICPPClassType) getSpecializedBinding();
ICPPClassType ct2= (ICPPClassType) ((ICPPTemplateInstance)type).getTemplateDefinition();
if(!ct1.isSameType(ct2))
return false;
ObjectMap m1 = getArgumentMap(), m2 = ((ICPPTemplateInstance)type).getArgumentMap();
if( m1 == null || m2 == null || m1.size() != m2.size())
return false;
for( int i = 0; i < m1.size(); i++ ){
IType t1 = (IType) m1.getAt( i );
IType t2 = (IType) m2.getAt( i );
if( t1 == null || ! t1.isSameType( t2 ) )
return false;
}
return true;
}
return false;
}
public ICPPClassType[] getNestedClasses() throws DOMException {
return ICPPClassType.EMPTY_CLASS_ARRAY;
}
public ICPPMethod[] getConversionOperators() throws DOMException {
IScope scope = getCompositeScope();
if (scope instanceof CPPClassSpecializationScope) {
if (ASTInternal.isFullyCached(scope))
return ((CPPClassSpecializationScope)scope).getConversionOperators();
}
return ICPPMethod.EMPTY_CPPMETHOD_ARRAY;
}
public boolean equals(Object obj) {
return obj instanceof ICPPClassType ? isSameType((ICPPClassType)obj) : false;
}

View file

@ -405,7 +405,7 @@ class ImplicitsAnalysis {
ICPPASTFunctionDeclarator dcltor= ctors[i];
IASTParameterDeclaration [] ps = dcltor.getParameters();
if( ps.length >= 1 ){
if(paramHasTypeReferenceToTheAssociatedClassType(ps[0])) {
if(paramHasTypeReferenceToTheAssociatedClassType(ps[0], compSpec.getName().getRawSignature())) {
// and all remaining arguments have initialisers
for(int j=1; j<ps.length; j++) {
if( ps[j].getDeclarator().getInitializer() == null ) {
@ -429,7 +429,7 @@ class ImplicitsAnalysis {
}
private static ICPPASTFunctionDeclarator[] getUserDeclaredCtorOrDtor( ICPPASTCompositeTypeSpecifier compSpec, boolean constructor ) {
List result= new ArrayList();
List<ICPPASTFunctionDeclarator> result= new ArrayList<ICPPASTFunctionDeclarator>();
IASTDeclaration [] members = compSpec.getMembers();
char [] name = compSpec.getName().toCharArray();
IASTDeclarator dcltor = null;
@ -466,13 +466,13 @@ class ImplicitsAnalysis {
if(!nameEquals)
continue;
result.add(dcltor);
result.add((ICPPASTFunctionDeclarator) dcltor);
}
return (ICPPASTFunctionDeclarator[]) result.toArray(new ICPPASTFunctionDeclarator[result.size()]);
return result.toArray(new ICPPASTFunctionDeclarator[result.size()]);
}
private static ICPPASTFunctionDeclarator[] getUserDeclaredCopyAssignmentOperators( ICPPASTCompositeTypeSpecifier compSpec ) {
List result= new ArrayList();
List<ICPPASTFunctionDeclarator> result= new ArrayList<ICPPASTFunctionDeclarator>();
IASTDeclaration [] members = compSpec.getMembers();
IASTDeclarator dcltor = null;
for( int i = 0; i < members.length; i++ ){
@ -491,20 +491,29 @@ class ImplicitsAnalysis {
}
IASTParameterDeclaration [] ps = ((ICPPASTFunctionDeclarator)dcltor).getParameters();
if( ps.length != 1 || !paramHasTypeReferenceToTheAssociatedClassType(ps[0]) )
if(ps.length != 1 || !paramHasTypeReferenceToTheAssociatedClassType(ps[0], null))
continue;
result.add(dcltor);
result.add((ICPPASTFunctionDeclarator)dcltor);
}
return (ICPPASTFunctionDeclarator[]) result.toArray(new ICPPASTFunctionDeclarator[result.size()]);
return result.toArray(new ICPPASTFunctionDeclarator[result.size()]);
}
private static boolean paramHasTypeReferenceToTheAssociatedClassType(IASTParameterDeclaration dec) {
/**
* @param compSpec the name the parameter must have in order to match, or null for any name
* @param dec
* @return whether the specified parameter is a reference to the associated class type, and
* (optionally) if it has the specified name
*/
private static boolean paramHasTypeReferenceToTheAssociatedClassType(IASTParameterDeclaration dec, String name) {
boolean result= false;
IASTDeclarator pdtor= dec.getDeclarator();
if(pdtor.getPointerOperators().length==1 && pdtor.getPointerOperators()[0] instanceof ICPPASTReferenceOperator) {
if(dec.getDeclSpecifier() instanceof ICPPASTNamedTypeSpecifier) {
result= true;
ICPPASTNamedTypeSpecifier nts= (ICPPASTNamedTypeSpecifier) dec.getDeclSpecifier();
if(name==null || name.equals(nts.getName().getRawSignature())) {
result= true;
}
}
}
return result;

View file

@ -10,9 +10,6 @@
* Markus Schorn (Wind River Systems)
* Bryan Wilkinson (QNX)
*******************************************************************************/
/*
* Created on Mar 28, 2005
*/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.IName;
@ -145,7 +142,7 @@ public class CPPClassSpecializationScope implements ICPPClassScope, IASTInternal
return (ICPPConstructor[]) ArrayUtil.trim(ICPPConstructor.class, specs);
}
protected ICPPMethod[] getConversionOperators() {
protected ICPPMethod[] getConversionOperators() throws DOMException {
ICPPClassType specialized = (ICPPClassType) specialization.getSpecializedBinding();
if (!(specialized instanceof ICPPInternalClassType)) {

View file

@ -9,23 +9,19 @@
* IBM - Initial API and implementation
* Bryan Wilkinson (QNX)
* Markus Schorn (Wind River Systems)
* Andrew Ferguson (Symbian)
*******************************************************************************/
/*
* Created on Mar 31, 2005
*/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IField;
import org.eclipse.cdt.core.dom.ast.IProblemBinding;
import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.ITypedef;
@ -35,9 +31,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTQualifiedName;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPBase;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassTemplate;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassTemplatePartialSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
@ -47,67 +41,62 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPField;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.CharArrayUtils;
import org.eclipse.cdt.core.parser.util.ObjectSet;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPClassType.CPPClassTypeProblem;
import org.eclipse.cdt.internal.core.index.IIndexType;
/**
*
* @author aniefer
*/
public class CPPClassTemplate extends CPPTemplateDefinition implements
ICPPClassTemplate, ICPPClassType, ICPPInternalClassType, ICPPInternalClassTemplate {
public static class CPPClassTemplateDelegate extends CPPClassType.CPPClassTypeDelegate implements ICPPClassTemplate, ICPPInternalClassTemplate {
public CPPClassTemplateDelegate( IASTName name, ICPPClassType cls ) {
super( name, cls );
}
public ICPPClassTemplatePartialSpecialization[] getPartialSpecializations() throws DOMException {
return ((ICPPClassTemplate)getBinding()).getPartialSpecializations();
}
public ICPPTemplateParameter[] getTemplateParameters() throws DOMException {
return ((ICPPClassTemplate)getBinding()).getTemplateParameters();
}
public void addSpecialization( IType[] arguments, ICPPSpecialization specialization ) {
final IBinding binding = getBinding();
if (binding instanceof ICPPInternalBinding) {
((ICPPInternalTemplate)binding).addSpecialization( arguments, specialization );
}
}
public IBinding instantiate( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).instantiate( arguments );
}
public ICPPSpecialization deferredInstance( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).deferredInstance( arguments );
}
public ICPPSpecialization getInstance( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).getInstance( arguments );
}
public void addPartialSpecialization( ICPPClassTemplatePartialSpecialization spec ) {
final IBinding binding = getBinding();
if (binding instanceof ICPPInternalClassTemplate) {
((ICPPInternalClassTemplate)getBinding()).addPartialSpecialization( spec );
}
ICPPClassTemplate, ICPPClassType, ICPPInternalClassType, ICPPInternalClassTemplate, ICPPInternalClassTypeMixinHost {
public static class CPPClassTemplateDelegate extends CPPClassType.CPPClassTypeDelegate implements ICPPClassTemplate, ICPPInternalClassTemplate {
public CPPClassTemplateDelegate( IASTName name, ICPPClassType cls ) {
super( name, cls );
}
}
private ICPPClassTemplatePartialSpecialization [] partialSpecializations = null;
public ICPPClassTemplatePartialSpecialization[] getPartialSpecializations() throws DOMException {
return ((ICPPClassTemplate)getBinding()).getPartialSpecializations();
}
public ICPPTemplateParameter[] getTemplateParameters() throws DOMException {
return ((ICPPClassTemplate)getBinding()).getTemplateParameters();
}
public void addSpecialization( IType[] arguments, ICPPSpecialization specialization ) {
final IBinding binding = getBinding();
if (binding instanceof ICPPInternalBinding) {
((ICPPInternalTemplate)binding).addSpecialization( arguments, specialization );
}
}
public IBinding instantiate( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).instantiate( arguments );
}
public ICPPSpecialization deferredInstance( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).deferredInstance( arguments );
}
public ICPPSpecialization getInstance( IType[] arguments ) {
return ((ICPPInternalTemplateInstantiator)getBinding()).getInstance( arguments );
}
public void addPartialSpecialization( ICPPClassTemplatePartialSpecialization spec ) {
final IBinding binding = getBinding();
if (binding instanceof ICPPInternalClassTemplate) {
((ICPPInternalClassTemplate)getBinding()).addPartialSpecialization( spec );
}
}
}
private class FindDefinitionAction extends CPPASTVisitor {
private char [] nameArray = CPPClassTemplate.this.getNameCharArray();
public IASTName result = null;
{
shouldVisitNames = true;
private char [] nameArray = CPPClassTemplate.this.getNameCharArray();
public IASTName result = null;
{
shouldVisitNames = true;
shouldVisitDeclarations = true;
shouldVisitDeclSpecifiers = true;
shouldVisitDeclarators = true;
}
public int visit( IASTName name ){
}
public int visit( IASTName name ){
if( name instanceof ICPPASTTemplateId || name instanceof ICPPASTQualifiedName )
return PROCESS_CONTINUE;
char [] c = name.toCharArray();
@ -119,38 +108,40 @@ public class CPPClassTemplate extends CPPTemplateDefinition implements
return PROCESS_CONTINUE;
name = (IASTName) name.getParent();
}
if( name.getParent() instanceof ICPPASTCompositeTypeSpecifier &&
CharArrayUtils.equals( c, nameArray ) )
{
IBinding binding = name.resolveBinding();
if( binding == CPPClassTemplate.this ){
if( name instanceof ICPPASTQualifiedName ){
IASTName [] ns = ((ICPPASTQualifiedName)name).getNames();
name = ns[ ns.length - 1 ];
}
result = name;
return PROCESS_ABORT;
}
}
return PROCESS_CONTINUE;
}
if( name.getParent() instanceof ICPPASTCompositeTypeSpecifier &&
CharArrayUtils.equals( c, nameArray ) )
{
IBinding binding = name.resolveBinding();
if( binding == CPPClassTemplate.this ){
if( name instanceof ICPPASTQualifiedName ){
IASTName [] ns = ((ICPPASTQualifiedName)name).getNames();
name = ns[ ns.length - 1 ];
}
result = name;
return PROCESS_ABORT;
}
}
return PROCESS_CONTINUE;
}
public int visit( IASTDeclaration declaration ){
if(declaration instanceof IASTSimpleDeclaration || declaration instanceof ICPPASTTemplateDeclaration )
if(declaration instanceof IASTSimpleDeclaration || declaration instanceof ICPPASTTemplateDeclaration)
return PROCESS_CONTINUE;
return PROCESS_SKIP;
}
public int visit( IASTDeclSpecifier declSpec ){
return (declSpec instanceof ICPPASTCompositeTypeSpecifier ) ? PROCESS_CONTINUE : PROCESS_SKIP;
return (declSpec instanceof ICPPASTCompositeTypeSpecifier ) ? PROCESS_CONTINUE : PROCESS_SKIP;
}
public int visit( IASTDeclarator declarator ) { return PROCESS_SKIP; }
}
/**
* @param decl
*/
public CPPClassTemplate(IASTName name) {
private ICPPClassTemplatePartialSpecialization [] partialSpecializations = null;
private ClassTypeMixin mixin;
public CPPClassTemplate(IASTName name) {
super(name);
this.mixin= new ClassTypeMixin(this);
}
public ICPPSpecialization deferredInstance( IType [] arguments ){
@ -161,310 +152,43 @@ public class CPPClassTemplate extends CPPTemplateDefinition implements
}
return instance;
}
private void checkForDefinition(){
public void checkForDefinition(){
FindDefinitionAction action = new FindDefinitionAction();
IASTNode node = CPPVisitor.getContainingBlockItem( declarations[0] ).getParent();
while( node instanceof ICPPASTTemplateDeclaration )
node = node.getParent();
node.accept( action );
definition = action.result;
definition = action.result;
if( definition == null ){
node.getTranslationUnit().accept( action );
definition = action.result;
definition = action.result;
}
return;
}
public void addPartialSpecialization( ICPPClassTemplatePartialSpecialization spec ){
partialSpecializations = (ICPPClassTemplatePartialSpecialization[]) ArrayUtil.append( ICPPClassTemplatePartialSpecialization.class, partialSpecializations, spec );
}
private ICPPASTCompositeTypeSpecifier getCompositeTypeSpecifier(){
if( definition != null ){
IASTNode node = definition.getParent();
if( node instanceof ICPPASTQualifiedName )
node = node.getParent();
if( node instanceof ICPPASTCompositeTypeSpecifier )
return (ICPPASTCompositeTypeSpecifier) node;
}
return null;
}
/**
* @param templateParameter
* @return
*/
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getBases()
*/
public ICPPBase [] getBases() {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTName node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPBase [] { new CPPBaseClause.CPPBaseProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
ICPPASTBaseSpecifier [] bases = getCompositeTypeSpecifier().getBaseSpecifiers();
if( bases.length == 0 )
return ICPPBase.EMPTY_BASE_ARRAY;
ICPPBase [] bindings = new ICPPBase[ bases.length ];
for( int i = 0; i < bases.length; i++ ){
bindings[i] = new CPPBaseClause( bases[i] );
public ICPPASTCompositeTypeSpecifier getCompositeTypeSpecifier(){
if( definition != null ){
IASTNode node = definition.getParent();
if( node instanceof ICPPASTQualifiedName )
node = node.getParent();
if( node instanceof ICPPASTCompositeTypeSpecifier )
return (ICPPASTCompositeTypeSpecifier) node;
}
return bindings;
return null;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.ICompositeType#getFields()
*/
public IField[] getFields() throws DOMException {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new IField [] { new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
IField[] fields = getDeclaredFields();
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
fields = (IField[]) ArrayUtil.addAll( IField.class, fields, ((ICPPClassType)b).getFields() );
}
return (IField[]) ArrayUtil.trim( IField.class, fields );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.ICompositeType#findField(java.lang.String)
*/
public IField findField(String name) throws DOMException {
IBinding [] bindings = CPPSemantics.findBindings( getCompositeScope(), name, true );
IField field = null;
for ( int i = 0; i < bindings.length; i++ ) {
if( bindings[i] instanceof IField ){
if( field == null )
field = (IField) bindings[i];
else {
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_AMBIGUOUS_LOOKUP, name.toCharArray() );
}
}
}
return field;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getDeclaredFields()
*/
public ICPPField[] getDeclaredFields() throws DOMException {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPField[] { new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPField [] result = null;
IASTDeclaration [] decls = getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
if( decls[i] instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decls[i]).getDeclarators();
for ( int j = 0; j < dtors.length; j++ ) {
binding = dtors[j].getName().resolveBinding();
if( binding instanceof ICPPField )
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, binding );
}
} else if( decls[i] instanceof ICPPASTUsingDeclaration ){
IASTName n = ((ICPPASTUsingDeclaration)decls[i]).getName();
binding = n.resolveBinding();
if( binding instanceof ICPPUsingDeclaration ){
IBinding [] bs = ((ICPPUsingDeclaration)binding).getDelegates();
for ( int j = 0; j < bs.length; j++ ) {
if( bs[j] instanceof ICPPField )
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, bs[j] );
}
} else if( binding instanceof ICPPField ) {
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, binding );
}
}
}
return (ICPPField[]) ArrayUtil.trim( ICPPField.class, result );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getMethods()
*/
public ICPPMethod[] getMethods() throws DOMException {
ObjectSet set = new ObjectSet(4);
set.addAll( getDeclaredMethods() );
ICPPClassScope scope = (ICPPClassScope) getCompositeScope();
set.addAll( scope.getImplicitMethods() );
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
set.addAll( ((ICPPClassType)b).getMethods() );
}
return (ICPPMethod[]) set.keyArray( ICPPMethod.class );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getAllDeclaredMethods()
*/
public ICPPMethod[] getAllDeclaredMethods() throws DOMException {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPMethod [] { new CPPMethod.CPPMethodProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
ICPPMethod[] methods = getDeclaredMethods();
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
methods = (ICPPMethod[]) ArrayUtil.addAll( ICPPMethod.class, methods, ((ICPPClassType)b).getAllDeclaredMethods() );
}
return (ICPPMethod[]) ArrayUtil.trim( ICPPMethod.class, methods );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getDeclaredMethods()
*/
public ICPPMethod[] getDeclaredMethods() throws DOMException {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPMethod[] { new CPPMethod.CPPMethodProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPMethod [] result = null;
IASTDeclaration [] decls = getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
IASTDeclaration decl = decls[i];
while( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decl).getDeclarators();
for ( int j = 0; j < dtors.length; j++ ) {
binding = dtors[j].getName().resolveBinding();
if( binding instanceof ICPPMethod)
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
} else if( decl instanceof IASTFunctionDefinition ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decl).getDeclarator();
dtor = CPPVisitor.getMostNestedDeclarator( dtor );
binding = dtor.getName().resolveBinding();
if( binding instanceof ICPPMethod ){
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
} else if( decl instanceof ICPPASTUsingDeclaration ){
IASTName n = ((ICPPASTUsingDeclaration)decl).getName();
binding = n.resolveBinding();
if( binding instanceof ICPPUsingDeclaration ){
IBinding [] bs = ((ICPPUsingDeclaration)binding).getDelegates();
for ( int j = 0; j < bs.length; j++ ) {
if( bs[j] instanceof ICPPMethod )
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, bs[j] );
}
} else if( binding instanceof ICPPMethod ) {
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
}
}
return (ICPPMethod[]) ArrayUtil.trim( ICPPMethod.class, result );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getConstructors()
*/
public ICPPConstructor[] getConstructors() throws DOMException {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPConstructor [] { new CPPConstructor.CPPConstructorProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
ICPPClassScope scope = (ICPPClassScope) getCompositeScope();
if( ASTInternal.isFullyCached(scope))
return ((CPPClassScope)scope).getConstructors( true );
IASTDeclaration [] members = getCompositeTypeSpecifier().getMembers();
for( int i = 0; i < members.length; i++ ){
IASTDeclaration decl = members[i];
if( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decl).getDeclarators();
for( int j = 0; j < dtors.length; j++ ){
if( dtors[j] == null ) break;
ASTInternal.addName(scope, dtors[j].getName() );
}
} else if( decl instanceof IASTFunctionDefinition ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decl).getDeclarator();
ASTInternal.addName(scope, dtor.getName() );
}
}
return ((CPPClassScope)scope).getConstructors( true );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getFriends()
*/
public IBinding[] getFriends() {
//TODO
return IBinding.EMPTY_BINDING_ARRAY;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.ICompositeType#getKey()
*/
public int getKey() {
if( definition != null ) {
ICPPASTCompositeTypeSpecifier cts= getCompositeTypeSpecifier();
if (cts != null) {
return cts.getKey();
}
IASTNode n= definition.getParent();
if (n instanceof ICPPASTElaboratedTypeSpecifier) {
return ((ICPPASTElaboratedTypeSpecifier)n).getKind();
}
}
if( declarations != null && declarations.length > 0 ){
IASTNode n = declarations[0].getParent();
if( n instanceof ICPPASTElaboratedTypeSpecifier ){
return ((ICPPASTElaboratedTypeSpecifier)n).getKind();
}
}
return ICPPASTElaboratedTypeSpecifier.k_class;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.ICompositeType#getCompositeScope()
*/
public IScope getCompositeScope() {
if( definition == null )
checkForDefinition();
if( definition != null ) {
if (definition == null) {
checkForDefinition();
}
if (definition != null) {
IASTNode parent = definition.getParent();
while (parent instanceof IASTName)
parent = parent.getParent();
@ -476,9 +200,93 @@ public class CPPClassTemplate extends CPPTemplateDefinition implements
return null;
}
/* (non-Javadoc)
* @see java.lang.Object#clone()
*/
public int getKey() {
if( definition != null ) {
ICPPASTCompositeTypeSpecifier cts= getCompositeTypeSpecifier();
if (cts != null) {
return cts.getKey();
}
IASTNode n= definition.getParent();
if (n instanceof ICPPASTElaboratedTypeSpecifier) {
return ((ICPPASTElaboratedTypeSpecifier)n).getKind();
}
}
if( declarations != null && declarations.length > 0 ){
IASTNode n = declarations[0].getParent();
if( n instanceof ICPPASTElaboratedTypeSpecifier ){
return ((ICPPASTElaboratedTypeSpecifier)n).getKind();
}
}
return ICPPASTElaboratedTypeSpecifier.k_class;
}
public ICPPClassTemplatePartialSpecialization[] getPartialSpecializations() {
partialSpecializations = (ICPPClassTemplatePartialSpecialization[]) ArrayUtil.trim( ICPPClassTemplatePartialSpecialization.class, partialSpecializations );
return partialSpecializations;
}
public ICPPDelegate createDelegate( IASTName name ) {
return new CPPClassTemplateDelegate( name, this );
}
/* */
public boolean isSameType( IType type ) {
if (type == this)
return true;
if (type instanceof ITypedef || type instanceof IIndexType || type instanceof ICPPDelegate)
return type.isSameType(this);
return false;
}
public ICPPBase [] getBases() {
return mixin.getBases();
}
public IField[] getFields() throws DOMException {
return mixin.getFields();
}
public ICPPField[] getDeclaredFields() throws DOMException {
return mixin.getDeclaredFields();
}
public ICPPMethod[] getConversionOperators() throws DOMException {
return mixin.getConversionOperators();
}
public ICPPMethod[] getMethods() throws DOMException {
return mixin.getMethods();
}
public ICPPMethod[] getAllDeclaredMethods() throws DOMException {
return mixin.getAllDeclaredMethods();
}
public ICPPMethod[] getDeclaredMethods() throws DOMException {
return mixin.getDeclaredMethods();
}
public ICPPConstructor[] getConstructors() throws DOMException {
return mixin.getConstructors();
}
public IBinding[] getFriends() {
return mixin.getFriends();
}
public ICPPClassType[] getNestedClasses() {
return mixin.getNestedClasses();
}
public IField findField(String name) throws DOMException {
return mixin.findField(name);
}
public Object clone() {
try {
return super.clone();
@ -486,66 +294,4 @@ public class CPPClassTemplate extends CPPTemplateDefinition implements
}
return null;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPInternalClassType#getConversionOperators()
*/
public ICPPMethod[] getConversionOperators() {
return ICPPMethod.EMPTY_CPPMETHOD_ARRAY;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.IType#isSameType(org.eclipse.cdt.core.dom.ast.IType)
*/
public boolean isSameType( IType type ) {
if( type == this )
return true;
if( type instanceof ITypedef || type instanceof IIndexType)
return type.isSameType( this );
return false;
}
public ICPPClassTemplatePartialSpecialization[] getPartialSpecializations() {
partialSpecializations = (ICPPClassTemplatePartialSpecialization[]) ArrayUtil.trim( ICPPClassTemplatePartialSpecialization.class, partialSpecializations );
return partialSpecializations;
}
/* (non-Javadoc)
* @see org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPInternalBinding#createDelegate(org.eclipse.cdt.core.dom.ast.IASTName)
*/
public ICPPDelegate createDelegate( IASTName name ) {
return new CPPClassTemplateDelegate( name, this );
}
public ICPPClassType[] getNestedClasses() {
if( definition == null ){
checkForDefinition();
if( definition == null ){
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPClassType[] { new CPPClassTypeProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPClassType [] result = null;
IASTDeclaration [] decls = getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
IASTDeclaration decl = decls[i];
while( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IASTDeclSpecifier declSpec = ((IASTSimpleDeclaration) decl).getDeclSpecifier();
if( declSpec instanceof ICPPASTCompositeTypeSpecifier ){
binding = ((ICPPASTCompositeTypeSpecifier)declSpec).getName().resolveBinding();
} else if( declSpec instanceof ICPPASTElaboratedTypeSpecifier &&
((IASTSimpleDeclaration)decl).getDeclarators().length == 0 )
{
binding = ((ICPPASTElaboratedTypeSpecifier)declSpec).getName().resolveBinding();
}
if( binding instanceof ICPPClassType )
result = (ICPPClassType[])ArrayUtil.append( ICPPClassType.class, result, binding );
}
}
return (ICPPClassType[]) ArrayUtil.trim( ICPPClassType.class, result );
}
}

View file

@ -0,0 +1,407 @@
/*******************************************************************************
* Copyright (c) 2004, 2007 IBM Corporation 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:
* IBM Corporation - initial API and implementation
* Markus Schorn (Wind River Systems)
* Bryan Wilkinson (QNX)
* Sergey Prigogin (Google)
* Andrew Ferguson (Symbian)
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IField;
import org.eclipse.cdt.core.dom.ast.IProblemBinding;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPBase;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPConstructor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPField;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.ObjectSet;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPClassType.CPPClassTypeProblem;
/**
* Holds common implementation of methods for ICPPClassType implementations that have
* a corresponding textual definition in the source code. This functionality is then
* accessed via a delegate.
*
* @see CPPClassType
* @see CPPClassTemplate
*/
class ClassTypeMixin {
private ICPPInternalClassTypeMixinHost host;
public ClassTypeMixin(ICPPInternalClassTypeMixinHost host) {
this.host= host;
}
public IBinding[] getFriends() {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new IBinding [] { new ProblemBinding( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
ObjectSet resultSet = new ObjectSet(2);
IASTDeclaration [] members = host.getCompositeTypeSpecifier().getMembers();
for( int i = 0; i < members.length; i++ ){
IASTDeclaration decl = members[i];
while( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
ICPPASTDeclSpecifier declSpec = (ICPPASTDeclSpecifier) ((IASTSimpleDeclaration)decl).getDeclSpecifier();
if( declSpec.isFriend() ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decl).getDeclarators();
if( declSpec instanceof ICPPASTElaboratedTypeSpecifier && dtors.length == 0 ){
resultSet.put( ((ICPPASTElaboratedTypeSpecifier)declSpec).getName().resolveBinding() );
} else {
for( int j = 0; j < dtors.length; j++ ){
if( dtors[j] == null ) break;
resultSet.put( dtors[j].getName().resolveBinding() );
}
}
}
} else if( decl instanceof IASTFunctionDefinition ){
ICPPASTDeclSpecifier declSpec = (ICPPASTDeclSpecifier) ((IASTFunctionDefinition)decl).getDeclSpecifier();
if( declSpec.isFriend() ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decl).getDeclarator();
resultSet.put( dtor.getName().resolveBinding() );
}
}
}
return (IBinding[]) resultSet.keyArray( IBinding.class );
}
public ICPPMethod[] getConversionOperators() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPMethod[] { new CPPMethod.CPPMethodProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPMethod [] result = null;
IASTDeclaration [] decls = host.getCompositeTypeSpecifier().getMembers();
IASTName name = null;
for ( int i = 0; i < decls.length; i++ ) {
if( decls[i] instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decls[i]).getDeclarators();
for ( int j = 0; j < dtors.length; j++ ) {
name = CPPVisitor.getMostNestedDeclarator( dtors[j] ).getName();
if( name instanceof ICPPASTConversionName ){
binding = name.resolveBinding();
if( binding instanceof ICPPMethod)
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
}
} else if( decls[i] instanceof IASTFunctionDefinition ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decls[i]).getDeclarator();
name = CPPVisitor.getMostNestedDeclarator( dtor ).getName();
if( name instanceof ICPPASTConversionName ){
binding = name.resolveBinding();
if( binding instanceof ICPPMethod ){
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
}
}
}
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
ICPPClassType cls = null;
try {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
cls = (ICPPClassType) b;
} catch (DOMException e) {
continue;
}
if( cls instanceof ICPPInternalClassType )
result = (ICPPMethod[]) ArrayUtil.addAll( ICPPMethod.class, result, ((ICPPInternalClassType)cls).getConversionOperators() );
}
return (ICPPMethod[]) ArrayUtil.trim( ICPPMethod.class, result );
}
public ICPPBase [] getBases() {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPBase [] { new CPPBaseClause.CPPBaseProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
ICPPASTBaseSpecifier [] bases = host.getCompositeTypeSpecifier().getBaseSpecifiers();
if( bases.length == 0 )
return ICPPBase.EMPTY_BASE_ARRAY;
ICPPBase [] bindings = new ICPPBase[ bases.length ];
for( int i = 0; i < bases.length; i++ ){
bindings[i] = new CPPBaseClause( bases[i] );
}
return bindings;
}
public ICPPMethod[] getMethods() throws DOMException {
ObjectSet set = new ObjectSet(4);
set.addAll(getDeclaredMethods());
ICPPClassScope scope = (ICPPClassScope) host.getCompositeScope();
set.addAll( scope.getImplicitMethods() );
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
set.addAll( ((ICPPClassType)b).getMethods() );
}
return (ICPPMethod[]) set.keyArray( ICPPMethod.class );
}
public ICPPField[] getDeclaredFields() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPField[] { new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPField [] result = null;
IASTDeclaration [] decls = host.getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
if( decls[i] instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decls[i]).getDeclarators();
for ( int j = 0; j < dtors.length; j++ ) {
binding = dtors[j].getName().resolveBinding();
if( binding instanceof ICPPField )
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, binding );
}
} else if( decls[i] instanceof ICPPASTUsingDeclaration ){
IASTName n = ((ICPPASTUsingDeclaration)decls[i]).getName();
binding = n.resolveBinding();
if( binding instanceof ICPPUsingDeclaration ){
IBinding [] bs = ((ICPPUsingDeclaration)binding).getDelegates();
for ( int j = 0; j < bs.length; j++ ) {
if( bs[j] instanceof ICPPField )
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, bs[j] );
}
} else if( binding instanceof ICPPField ) {
result = (ICPPField[]) ArrayUtil.append( ICPPField.class, result, binding );
}
}
}
return (ICPPField[]) ArrayUtil.trim( ICPPField.class, result );
}
public ICPPMethod[] getAllDeclaredMethods() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPMethod [] { new CPPMethod.CPPMethodProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
ICPPMethod[] methods = getDeclaredMethods();
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
methods = (ICPPMethod[]) ArrayUtil.addAll( ICPPMethod.class, methods, ((ICPPClassType)b).getAllDeclaredMethods() );
}
return (ICPPMethod[]) ArrayUtil.trim( ICPPMethod.class, methods );
}
public ICPPMethod[] getDeclaredMethods() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPMethod[] { new CPPMethod.CPPMethodProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
IBinding binding = null;
ICPPMethod [] result = null;
IASTDeclaration [] decls = host.getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
IASTDeclaration decl = decls[i];
while( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decl).getDeclarators();
for ( int j = 0; j < dtors.length; j++ ) {
binding = dtors[j].getName().resolveBinding();
if( binding instanceof ICPPMethod)
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
} else if( decl instanceof IASTFunctionDefinition ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decl).getDeclarator();
dtor = CPPVisitor.getMostNestedDeclarator( dtor );
binding = dtor.getName().resolveBinding();
if( binding instanceof ICPPMethod ){
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
} else if( decl instanceof ICPPASTUsingDeclaration ){
IASTName n = ((ICPPASTUsingDeclaration)decl).getName();
binding = n.resolveBinding();
if( binding instanceof ICPPUsingDeclaration ){
IBinding [] bs = ((ICPPUsingDeclaration)binding).getDelegates();
for ( int j = 0; j < bs.length; j++ ) {
if( bs[j] instanceof ICPPMethod )
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, bs[j] );
}
} else if( binding instanceof ICPPMethod ) {
result = (ICPPMethod[]) ArrayUtil.append( ICPPMethod.class, result, binding );
}
}
}
return (ICPPMethod[]) ArrayUtil.trim( ICPPMethod.class, result );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType#getConstructors()
*/
public ICPPConstructor[] getConstructors() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPConstructor [] { new CPPConstructor.CPPConstructorProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
ICPPClassScope scope = (ICPPClassScope) host.getCompositeScope();
if(ASTInternal.isFullyCached(scope))
return ((CPPClassScope)scope).getConstructors( true );
IASTDeclaration [] members = host.getCompositeTypeSpecifier().getMembers();
for( int i = 0; i < members.length; i++ ){
IASTDeclaration decl = members[i];
if( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IASTDeclarator [] dtors = ((IASTSimpleDeclaration)decl).getDeclarators();
for( int j = 0; j < dtors.length; j++ ){
if( dtors[j] == null ) break;
ASTInternal.addName(scope, dtors[j].getName() );
}
} else if( decl instanceof IASTFunctionDefinition ){
IASTDeclarator dtor = ((IASTFunctionDefinition)decl).getDeclarator();
ASTInternal.addName(scope, dtor.getName() );
}
}
return ((CPPClassScope)scope).getConstructors( true );
}
public ICPPClassType[] getNestedClasses() {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new ICPPClassType[] { new CPPClassTypeProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
ICPPClassType [] result = null;
IASTDeclaration [] decls = host.getCompositeTypeSpecifier().getMembers();
for ( int i = 0; i < decls.length; i++ ) {
IASTDeclaration decl = decls[i];
while( decl instanceof ICPPASTTemplateDeclaration )
decl = ((ICPPASTTemplateDeclaration)decl).getDeclaration();
if( decl instanceof IASTSimpleDeclaration ){
IBinding binding = null;
IASTDeclSpecifier declSpec = ((IASTSimpleDeclaration) decl).getDeclSpecifier();
if( declSpec instanceof ICPPASTCompositeTypeSpecifier ){
binding = ((ICPPASTCompositeTypeSpecifier)declSpec).getName().resolveBinding();
} else if( declSpec instanceof ICPPASTElaboratedTypeSpecifier &&
((IASTSimpleDeclaration)decl).getDeclarators().length == 0 )
{
binding = ((ICPPASTElaboratedTypeSpecifier)declSpec).getName().resolveBinding();
}
if( binding instanceof ICPPClassType )
result = (ICPPClassType[])ArrayUtil.append( ICPPClassType.class, result, binding );
}
}
return (ICPPClassType[]) ArrayUtil.trim( ICPPClassType.class, result );
}
public IField[] getFields() throws DOMException {
if( host.getDefinition() == null ){
host.checkForDefinition();
if( host.getDefinition() == null ){
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new IField [] { new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, host.getNameCharArray() ) };
}
}
IField[] fields = getDeclaredFields();
ICPPBase [] bases = getBases();
for ( int i = 0; i < bases.length; i++ ) {
IBinding b = bases[i].getBaseClass();
if( b instanceof ICPPClassType )
fields = (IField[]) ArrayUtil.addAll( IField.class, fields, ((ICPPClassType)b).getFields() );
}
return (IField[]) ArrayUtil.trim( IField.class, fields );
}
public IField findField(String name) throws DOMException {
IBinding [] bindings = CPPSemantics.findBindings( host.getCompositeScope(), name, true );
IField field = null;
for ( int i = 0; i < bindings.length; i++ ) {
if( bindings[i] instanceof IField ){
if( field == null )
field = (IField) bindings[i];
else {
IASTNode[] declarations= host.getDeclarations();
IASTNode node = (declarations != null && declarations.length > 0) ? declarations[0] : null;
return new CPPField.CPPFieldProblem( node, IProblemBinding.SEMANTIC_AMBIGUOUS_LOOKUP, name.toCharArray() );
}
}
}
return field;
}
}

View file

@ -13,11 +13,12 @@
*/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
/**
* @author aniefer
*/
public interface ICPPInternalClassType extends ICPPInternalBinding {
public ICPPMethod [] getConversionOperators();
public ICPPMethod [] getConversionOperators() throws DOMException;
}

View file

@ -0,0 +1,20 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
/**
* Internal interface for exposing internal methods to ClassTypeMixin
*/
interface ICPPInternalClassTypeMixinHost extends ICPPInternalClassType, ICPPClassType {
/**
* @return the composite type specifier for the class type
*/
ICPPASTCompositeTypeSpecifier getCompositeTypeSpecifier();
/**
* Ensures the ICPPInternalBinding definition is set, if this is possible.
* @see ICPPInternalBinding#getDefinition()
*/
void checkForDefinition();
}