Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
Diffstat (limited to 'core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java')
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java236
1 files changed, 68 insertions, 168 deletions
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java
index 0792dceece0..3f7f1473b53 100644
--- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/CPPASTFieldReference.java
@@ -14,57 +14,45 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import static org.eclipse.cdt.core.dom.ast.IASTExpression.ValueCategory.LVALUE;
-import static org.eclipse.cdt.core.dom.ast.IASTExpression.ValueCategory.PRVALUE;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.ExpressionTypes.glvalueType;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.ExpressionTypes.prvalueType;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.ExpressionTypes.prvalueTypeWithResolvedTypedefs;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.ExpressionTypes.typeFromFunctionCall;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.ALLCVQ;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.CVTYPE;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.REF;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.TDEF;
-import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.getUltimateTypeUptoPointers;
import java.util.ArrayList;
-import java.util.Collection;
import java.util.List;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
-import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTImplicitName;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.ICPPASTCompletionContext;
-import org.eclipse.cdt.core.dom.ast.IEnumerator;
-import org.eclipse.cdt.core.dom.ast.IFunction;
-import org.eclipse.cdt.core.dom.ast.IPointerType;
import org.eclipse.cdt.core.dom.ast.IProblemBinding;
-import org.eclipse.cdt.core.dom.ast.ISemanticProblem;
import org.eclipse.cdt.core.dom.ast.IType;
-import org.eclipse.cdt.core.dom.ast.IVariable;
+import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference;
-import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
-import org.eclipse.cdt.core.dom.ast.cpp.ICPPField;
+import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTQualifiedName;
+import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
+import org.eclipse.cdt.core.dom.ast.cpp.ICPPConstructor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunction;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
-import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
+import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
-import org.eclipse.cdt.internal.core.dom.parser.ProblemType;
+import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPFunctionSet;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPSemantics;
-import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CVQualifier;
-import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
+import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPTemplates;
+import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.EvalFixed;
+import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.EvalID;
+import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.EvalMemberAccess;
public class CPPASTFieldReference extends ASTNode
implements ICPPASTFieldReference, IASTAmbiguityParent, ICPPASTCompletionContext {
private boolean isTemplate;
- private IASTExpression owner;
+ private ICPPASTExpression owner;
private IASTName name;
private boolean isDeref;
private IASTImplicitName[] implicitNames;
+ private ICPPEvaluation fEvaluation;
public CPPASTFieldReference() {
}
@@ -73,11 +61,6 @@ public class CPPASTFieldReference extends ASTNode
setFieldName(name);
setFieldOwner(owner);
}
- @Override
- public ICPPInitClauseEvaluation getEvaluation() {
- // mstodo Auto-generated method stub
- return null;
- }
@Override
public CPPASTFieldReference copy() {
@@ -110,14 +93,14 @@ public class CPPASTFieldReference extends ASTNode
}
@Override
- public IASTExpression getFieldOwner() {
+ public ICPPASTExpression getFieldOwner() {
return owner;
}
@Override
public void setFieldOwner(IASTExpression expression) {
assertNotFrozen();
- owner = expression;
+ owner = (ICPPASTExpression) expression;
if (expression != null) {
expression.setParent(this);
expression.setPropertyInParent(FIELD_OWNER);
@@ -158,7 +141,7 @@ public class CPPASTFieldReference extends ASTNode
// Collect the function bindings
List<ICPPFunction> functionBindings = new ArrayList<ICPPFunction>();
- getFieldOwnerType(functionBindings);
+ EvalMemberAccess.getFieldOwnerType(owner.getExpressionType(), isDeref, this, functionBindings, false);
if (functionBindings.isEmpty())
return implicitNames = IASTImplicitName.EMPTY_NAME_ARRAY;
@@ -224,100 +207,10 @@ public class CPPASTFieldReference extends ASTNode
if (child == owner) {
other.setPropertyInParent(child.getPropertyInParent());
other.setParent(child.getParent());
- owner = (IASTExpression) other;
+ owner = (ICPPASTExpression) other;
}
}
- @Override
- public IType getExpressionType() {
- IASTName name= getFieldName();
- IBinding binding = name.resolvePreBinding();
- try {
- if (binding instanceof IVariable) {
- IType e2= ((IVariable) binding).getType();
- e2= SemanticUtil.getNestedType(e2, TDEF);
- if (e2 instanceof ICPPReferenceType) {
- e2= glvalueType(e2);
- } else if (binding instanceof ICPPField && !((ICPPField) binding).isStatic()) {
- IType e1= getFieldOwner().getExpressionType();
- if (isPointerDereference()) {
- e1= SemanticUtil.getNestedType(e1, TDEF | REF | CVTYPE);
- if (e1 instanceof IPointerType) {
- e1= ((IPointerType) e1).getType();
- }
- }
- e2 = addQualifiersForAccess((ICPPField) binding, e2, e1);
- if (!isPointerDereference() && owner.getValueCategory() == PRVALUE) {
- e2= prvalueType(e2);
- } else {
- e2= glvalueType(e2);
- }
- }
- return SemanticUtil.mapToAST(e2, this);
- }
- if (binding instanceof IEnumerator) {
- return ((IEnumerator) binding).getType();
- }
- if (binding instanceof IFunction) {
- return SemanticUtil.mapToAST(((IFunction) binding).getType(), this);
- }
- if (binding instanceof ICPPUnknownBinding) {
- // mstodo type of unknown.
- return CPPUnknownClass.createUnnamedInstance();
- }
- if (binding instanceof IProblemBinding) {
- return new ProblemType(ISemanticProblem.TYPE_UNRESOLVED_NAME);
- }
- return new ProblemType(ISemanticProblem.TYPE_UNKNOWN_FOR_EXPRESSION);
- } catch (DOMException e) {
- return e.getProblem();
- }
- }
-
- public static IType addQualifiersForAccess(ICPPField field, IType fieldType, IType ownerType) {
- CVQualifier cvq1 = SemanticUtil.getCVQualifier(ownerType);
- CVQualifier cvq2 = SemanticUtil.getCVQualifier(fieldType);
- if (field.isMutable()) {
- // Remove const, add union of volatile.
- if (cvq2.isConst()) {
- fieldType= SemanticUtil.getNestedType(fieldType, ALLCVQ | TDEF | REF);
- }
- fieldType= SemanticUtil.addQualifiers(fieldType, false, cvq1.isVolatile() || cvq2.isVolatile(), cvq2.isRestrict());
- } else {
- fieldType= SemanticUtil.addQualifiers(fieldType, cvq1.isConst(), cvq1.isVolatile(), cvq2.isRestrict());
- }
- return fieldType;
- }
-
- @Override
- public ValueCategory getValueCategory() {
- IASTName name= getFieldName();
- IBinding binding = name.resolvePreBinding();
- if (binding instanceof IVariable) {
- IType e2= ((IVariable) binding).getType();
- e2= SemanticUtil.getNestedType(e2, TDEF);
- if (e2 instanceof ICPPReferenceType) {
- return LVALUE;
- }
- if (binding instanceof ICPPField && !((ICPPField) binding).isStatic()) {
- if (isPointerDereference())
- return LVALUE;
-
- return owner.getValueCategory();
- }
- return LVALUE;
- }
- if (binding instanceof IFunction) {
- return LVALUE;
- }
- return PRVALUE;
- }
-
- @Override
- public boolean isLValue() {
- return getValueCategory() == LVALUE;
- }
-
@Override
public IBinding[] findBindings(IASTName n, boolean isPrefix, String[] namespaces) {
IBinding[] bindings = CPPSemantics.findBindingsForContentAssist(n, isPrefix, namespaces);
@@ -347,56 +240,63 @@ public class CPPASTFieldReference extends ASTNode
*/
@Override
public IType getFieldOwnerType() {
- return getFieldOwnerType(null);
+ return EvalMemberAccess.getFieldOwnerType(owner.getExpressionType(), isDeref, this, null, true);
}
- /*
- * Also collects the function bindings if requested.
- */
- private IType getFieldOwnerType(Collection<ICPPFunction> functionBindings) {
- final IASTExpression owner = getFieldOwner();
- if (owner == null)
- return null;
-
- IType type= owner.getExpressionType();
- if (!isPointerDereference())
- return type;
-
- // bug 205964: as long as the type is a class type, recurse.
- // Be defensive and allow a max of 20 levels.
- for (int j = 0; j < 20; j++) {
- // for unknown types we cannot determine the overloaded -> operator
- IType classType= getUltimateTypeUptoPointers(type);
- if (classType instanceof ICPPUnknownType)
- return CPPUnknownClass.createUnnamedInstance();
+ @Override
+ public ICPPEvaluation getEvaluation() {
+ if (fEvaluation == null) {
+ fEvaluation= createEvaluation();
+ }
+ return fEvaluation;
+ }
+
+ private ICPPEvaluation createEvaluation() {
+ ICPPEvaluation ownerEval = owner.getEvaluation();
+ if (!ownerEval.isTypeDependent()) {
+ IType ownerType= EvalMemberAccess.getFieldOwnerType(ownerEval.getTypeOrFunctionSet(this), isDeref, this, null, false);
+ if (ownerType != null) {
+ IBinding binding = name.resolvePreBinding();
+ if (binding instanceof CPPFunctionSet)
+ binding= name.resolveBinding();
- if (!(classType instanceof ICPPClassType))
- break;
-
- /*
- * 13.5.6-1: An expression x->m is interpreted as (x.operator->())->m for a
- * class object x of type T
- *
- * Construct an AST fragment for x.operator-> which the lookup routines can
- * examine for type information.
- */
+ if (binding instanceof IProblemBinding || binding instanceof IType || binding instanceof ICPPConstructor)
+ return EvalFixed.INCOMPLETE;
- ICPPFunction op = CPPSemantics.findOverloadedOperator(this, type, (ICPPClassType) classType);
- if (op == null)
- break;
+ return new EvalMemberAccess(ownerType, ownerEval.getValueCategory(this), binding, isDeref);
+ }
+ }
- if (functionBindings != null)
- functionBindings.add(op);
-
- type= typeFromFunctionCall(op);
- type= SemanticUtil.mapToAST(type, owner);
- }
-
- IType prValue= prvalueTypeWithResolvedTypedefs(type);
- if (prValue instanceof IPointerType) {
- return glvalueType(((IPointerType) prValue).getType());
+ IBinding qualifier= null;
+ ICPPTemplateArgument[] args= null;
+ IASTName n= name;
+ if (n instanceof ICPPASTQualifiedName) {
+ IASTName[] ns= ((ICPPASTQualifiedName) n).getNames();
+ if (ns.length < 2)
+ return EvalFixed.INCOMPLETE;
+ qualifier= ns[ns.length-2].resolveBinding();
+ if (qualifier instanceof IProblemBinding)
+ return EvalFixed.INCOMPLETE;
+ n= ns[ns.length-1];
}
+ if (n instanceof ICPPASTTemplateId) {
+ args= CPPTemplates.createTemplateArgumentArray((ICPPASTTemplateId) n);
+ }
+ return new EvalID(ownerEval, qualifier, name.getSimpleID(), false, qualifier != null, args);
+ }
- return new ProblemType(ISemanticProblem.TYPE_UNKNOWN_FOR_EXPRESSION);
- }
+ @Override
+ public IType getExpressionType() {
+ return getEvaluation().getTypeOrFunctionSet(this);
+ }
+
+ @Override
+ public boolean isLValue() {
+ return getValueCategory() == LVALUE;
+ }
+
+ @Override
+ public ValueCategory getValueCategory() {
+ return getEvaluation().getValueCategory(this);
+ }
}

Back to the top