mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-07-15 21:15:23 +02:00
Implemented is_empty type trait.
Change-Id: I1bb6fc98920eded16186889d66e33a7ca7432456
This commit is contained in:
parent
f3ff649041
commit
ec9a9fb5c7
3 changed files with 129 additions and 32 deletions
|
@ -1,5 +1,5 @@
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
* Copyright (c) 2011, 2013 Google, Inc and others.
|
* Copyright (c) 2011, 2016 Google, Inc and others.
|
||||||
* All rights reserved. This program and the accompanying materials
|
* All rights reserved. This program and the accompanying materials
|
||||||
* are made available under the terms of the Eclipse Public License v1.0
|
* are made available under the terms of the Eclipse Public License v1.0
|
||||||
* which accompanies this distribution, and is available at
|
* which accompanies this distribution, and is available at
|
||||||
|
@ -12,12 +12,13 @@ package org.eclipse.cdt.core.parser.tests.ast2;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
import junit.framework.TestSuite;
|
import org.eclipse.cdt.core.dom.ast.IType;
|
||||||
|
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
|
||||||
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.TypeTraits;
|
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.TypeTraits;
|
||||||
import org.eclipse.cdt.internal.core.parser.ParserException;
|
import org.eclipse.cdt.internal.core.parser.ParserException;
|
||||||
|
|
||||||
|
import junit.framework.TestSuite;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tests for ClassTypeHelper class.
|
* Tests for ClassTypeHelper class.
|
||||||
*/
|
*/
|
||||||
|
@ -58,11 +59,11 @@ public class TypeTraitsTests extends AST2TestBase {
|
||||||
// };
|
// };
|
||||||
public void testHasTrivialCopyCtor() throws Exception {
|
public void testHasTrivialCopyCtor() throws Exception {
|
||||||
BindingAssertionHelper helper = getAssertionHelper();
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
ICPPClassType classA = helper.assertNonProblem("A {", 1, ICPPClassType.class);
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
assertFalse(TypeTraits.hasTrivialCopyCtor(classA, null));
|
assertFalse(TypeTraits.hasTrivialCopyCtor(classA, null));
|
||||||
ICPPClassType classB = helper.assertNonProblem("B {", 1, ICPPClassType.class);
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B {");
|
||||||
assertTrue(TypeTraits.hasTrivialCopyCtor(classB, null));
|
assertTrue(TypeTraits.hasTrivialCopyCtor(classB, null));
|
||||||
ICPPClassType classC = helper.assertNonProblem("C {", 1, ICPPClassType.class);
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C {");
|
||||||
assertFalse(TypeTraits.hasTrivialCopyCtor(classC, null));
|
assertFalse(TypeTraits.hasTrivialCopyCtor(classC, null));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -86,14 +87,69 @@ public class TypeTraitsTests extends AST2TestBase {
|
||||||
// };
|
// };
|
||||||
public void testHasTrivialDestructor() throws Exception {
|
public void testHasTrivialDestructor() throws Exception {
|
||||||
BindingAssertionHelper helper = getAssertionHelper();
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
ICPPClassType classA = helper.assertNonProblem("A {", 1, ICPPClassType.class);
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
assertFalse(TypeTraits.hasTrivialDestructor(classA, null));
|
assertFalse(TypeTraits.hasTrivialDestructor(classA, null));
|
||||||
ICPPClassType classB = helper.assertNonProblem("B {", 1, ICPPClassType.class);
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B {");
|
||||||
assertTrue(TypeTraits.hasTrivialDestructor(classB, null));
|
assertTrue(TypeTraits.hasTrivialDestructor(classB, null));
|
||||||
ICPPClassType classC = helper.assertNonProblem("C {", 1, ICPPClassType.class);
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C {");
|
||||||
assertFalse(TypeTraits.hasTrivialDestructor(classC, null));
|
assertFalse(TypeTraits.hasTrivialDestructor(classC, null));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// struct A {
|
||||||
|
// static int x;
|
||||||
|
// ~A();
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// class B : public A {
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// struct C {
|
||||||
|
// A a;
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// struct D : public A, C {
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// struct E {
|
||||||
|
// virtual ~E();
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// struct F {
|
||||||
|
// virtual void m();
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// struct G : public virtual A {
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// typedef const A H;
|
||||||
|
//
|
||||||
|
// typedef A* I;
|
||||||
|
//
|
||||||
|
// typedef A J[0];
|
||||||
|
public void testIsEmpty() throws Exception {
|
||||||
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
|
assertTrue(TypeTraits.isEmpty(classA, null));
|
||||||
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B :");
|
||||||
|
assertTrue(TypeTraits.isEmpty(classB, null));
|
||||||
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C {");
|
||||||
|
assertFalse(TypeTraits.isEmpty(classC, null));
|
||||||
|
ICPPClassType classD = helper.assertNonProblemOnFirstIdentifier("D :");
|
||||||
|
assertFalse(TypeTraits.isEmpty(classD, null));
|
||||||
|
ICPPClassType classE = helper.assertNonProblemOnFirstIdentifier("E {");
|
||||||
|
assertFalse(TypeTraits.isEmpty(classE, null));
|
||||||
|
ICPPClassType classF = helper.assertNonProblemOnFirstIdentifier("F {");
|
||||||
|
assertFalse(TypeTraits.isEmpty(classF, null));
|
||||||
|
ICPPClassType classG = helper.assertNonProblemOnFirstIdentifier("G :");
|
||||||
|
assertFalse(TypeTraits.isEmpty(classG, null));
|
||||||
|
IType typeH = helper.assertNonProblemOnFirstIdentifier("H;");
|
||||||
|
assertTrue(TypeTraits.isEmpty(typeH, null));
|
||||||
|
IType typeI = helper.assertNonProblemOnFirstIdentifier("I;");
|
||||||
|
assertFalse(TypeTraits.isEmpty(typeI, null));
|
||||||
|
IType typeJ = helper.assertNonProblemOnFirstIdentifier("J[");
|
||||||
|
assertFalse(TypeTraits.isEmpty(typeJ, null));
|
||||||
|
}
|
||||||
|
|
||||||
// struct A {
|
// struct A {
|
||||||
// virtual void m();
|
// virtual void m();
|
||||||
// };
|
// };
|
||||||
|
@ -112,11 +168,11 @@ public class TypeTraitsTests extends AST2TestBase {
|
||||||
// };
|
// };
|
||||||
public void testIsPolymorphic() throws Exception {
|
public void testIsPolymorphic() throws Exception {
|
||||||
BindingAssertionHelper helper = getAssertionHelper();
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
ICPPClassType classA = helper.assertNonProblem("A {", 1, ICPPClassType.class);
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
assertTrue(TypeTraits.isPolymorphic(classA, null));
|
assertTrue(TypeTraits.isPolymorphic(classA, null));
|
||||||
ICPPClassType classB = helper.assertNonProblem("B {", 1, ICPPClassType.class);
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B {");
|
||||||
assertFalse(TypeTraits.isPolymorphic(classB, null));
|
assertFalse(TypeTraits.isPolymorphic(classB, null));
|
||||||
ICPPClassType classC = helper.assertNonProblem("C", 1, ICPPClassType.class);
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C");
|
||||||
assertTrue(TypeTraits.isPolymorphic(classC, null));
|
assertTrue(TypeTraits.isPolymorphic(classC, null));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -159,21 +215,21 @@ public class TypeTraitsTests extends AST2TestBase {
|
||||||
// };
|
// };
|
||||||
public void testIsStandardLayout() throws Exception {
|
public void testIsStandardLayout() throws Exception {
|
||||||
BindingAssertionHelper helper = getAssertionHelper();
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
ICPPClassType classA = helper.assertNonProblem("A {", 1, ICPPClassType.class);
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
assertTrue(TypeTraits.isStandardLayout(classA, null));
|
assertTrue(TypeTraits.isStandardLayout(classA, null));
|
||||||
ICPPClassType classB = helper.assertNonProblem("B {", 1, ICPPClassType.class);
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B {");
|
||||||
assertTrue(TypeTraits.isStandardLayout(classB, null));
|
assertTrue(TypeTraits.isStandardLayout(classB, null));
|
||||||
ICPPClassType classC = helper.assertNonProblem("C :", 1, ICPPClassType.class);
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C :");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classC, null));
|
assertFalse(TypeTraits.isStandardLayout(classC, null));
|
||||||
ICPPClassType classD = helper.assertNonProblem("D {", 1, ICPPClassType.class);
|
ICPPClassType classD = helper.assertNonProblemOnFirstIdentifier("D {");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classD, null));
|
assertFalse(TypeTraits.isStandardLayout(classD, null));
|
||||||
ICPPClassType classE = helper.assertNonProblem("E :", 1, ICPPClassType.class);
|
ICPPClassType classE = helper.assertNonProblemOnFirstIdentifier("E :");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classE, null));
|
assertFalse(TypeTraits.isStandardLayout(classE, null));
|
||||||
ICPPClassType classF = helper.assertNonProblem("F :", 1, ICPPClassType.class);
|
ICPPClassType classF = helper.assertNonProblemOnFirstIdentifier("F :");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classF, null));
|
assertFalse(TypeTraits.isStandardLayout(classF, null));
|
||||||
ICPPClassType classG = helper.assertNonProblem("G {", 1, ICPPClassType.class);
|
ICPPClassType classG = helper.assertNonProblemOnFirstIdentifier("G {");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classG, null));
|
assertFalse(TypeTraits.isStandardLayout(classG, null));
|
||||||
ICPPClassType classH = helper.assertNonProblem("H {", 1, ICPPClassType.class);
|
ICPPClassType classH = helper.assertNonProblemOnFirstIdentifier("H {");
|
||||||
assertFalse(TypeTraits.isStandardLayout(classH, null));
|
assertFalse(TypeTraits.isStandardLayout(classH, null));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -217,23 +273,23 @@ public class TypeTraitsTests extends AST2TestBase {
|
||||||
// };
|
// };
|
||||||
public void testIsTrivial() throws Exception {
|
public void testIsTrivial() throws Exception {
|
||||||
BindingAssertionHelper helper = getAssertionHelper();
|
BindingAssertionHelper helper = getAssertionHelper();
|
||||||
ICPPClassType classA = helper.assertNonProblem("A {", 1, ICPPClassType.class);
|
ICPPClassType classA = helper.assertNonProblemOnFirstIdentifier("A {");
|
||||||
assertTrue(TypeTraits.isTrivial(classA, null));
|
assertTrue(TypeTraits.isTrivial(classA, null));
|
||||||
ICPPClassType classB = helper.assertNonProblem("B :", 1, ICPPClassType.class);
|
ICPPClassType classB = helper.assertNonProblemOnFirstIdentifier("B :");
|
||||||
assertTrue(TypeTraits.isTrivial(classB, null));
|
assertTrue(TypeTraits.isTrivial(classB, null));
|
||||||
ICPPClassType classC = helper.assertNonProblem("C {", 1, ICPPClassType.class);
|
ICPPClassType classC = helper.assertNonProblemOnFirstIdentifier("C {");
|
||||||
assertFalse(TypeTraits.isTrivial(classC, null));
|
assertFalse(TypeTraits.isTrivial(classC, null));
|
||||||
ICPPClassType classD = helper.assertNonProblem("D {", 1, ICPPClassType.class);
|
ICPPClassType classD = helper.assertNonProblemOnFirstIdentifier("D {");
|
||||||
assertFalse(TypeTraits.isTrivial(classD, null));
|
assertFalse(TypeTraits.isTrivial(classD, null));
|
||||||
ICPPClassType classE = helper.assertNonProblem("E {", 1, ICPPClassType.class);
|
ICPPClassType classE = helper.assertNonProblemOnFirstIdentifier("E {");
|
||||||
assertFalse(TypeTraits.isTrivial(classE, null));
|
assertFalse(TypeTraits.isTrivial(classE, null));
|
||||||
ICPPClassType classF = helper.assertNonProblem("F {", 1, ICPPClassType.class);
|
ICPPClassType classF = helper.assertNonProblemOnFirstIdentifier("F {");
|
||||||
assertFalse(TypeTraits.isTrivial(classF, null));
|
assertFalse(TypeTraits.isTrivial(classF, null));
|
||||||
ICPPClassType classG = helper.assertNonProblem("G {", 1, ICPPClassType.class);
|
ICPPClassType classG = helper.assertNonProblemOnFirstIdentifier("G {");
|
||||||
assertFalse(TypeTraits.isTrivial(classG, null));
|
assertFalse(TypeTraits.isTrivial(classG, null));
|
||||||
ICPPClassType classH = helper.assertNonProblem("H :", 1, ICPPClassType.class);
|
ICPPClassType classH = helper.assertNonProblemOnFirstIdentifier("H :");
|
||||||
assertFalse(TypeTraits.isTrivial(classH, null));
|
assertFalse(TypeTraits.isTrivial(classH, null));
|
||||||
ICPPClassType classI = helper.assertNonProblem("I {", 1, ICPPClassType.class);
|
ICPPClassType classI = helper.assertNonProblemOnFirstIdentifier("I {");
|
||||||
assertFalse(TypeTraits.isTrivial(classI, null));
|
assertFalse(TypeTraits.isTrivial(classI, null));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
* Copyright (c) 2008, 2015 Wind River Systems, Inc. and others.
|
* Copyright (c) 2008, 2016 Wind River Systems, Inc. and others.
|
||||||
* All rights reserved. This program and the accompanying materials
|
* All rights reserved. This program and the accompanying materials
|
||||||
* are made available under the terms of the Eclipse Public License v1.0
|
* are made available under the terms of the Eclipse Public License v1.0
|
||||||
* which accompanies this distribution, and is available at
|
* which accompanies this distribution, and is available at
|
||||||
|
@ -333,7 +333,7 @@ public class Value implements IValue {
|
||||||
return type instanceof ICompositeType &&
|
return type instanceof ICompositeType &&
|
||||||
((ICompositeType) type).getKey() != ICompositeType.k_union ? 1 : 0;
|
((ICompositeType) type).getKey() != ICompositeType.k_union ? 1 : 0;
|
||||||
case op_is_empty:
|
case op_is_empty:
|
||||||
break; // TODO(sprigogin): Implement
|
return TypeTraits.isEmpty(type, point) ? 1 : 0;
|
||||||
case op_is_enum:
|
case op_is_enum:
|
||||||
return type instanceof IEnumeration ? 1 : 0;
|
return type instanceof IEnumeration ? 1 : 0;
|
||||||
case op_is_final:
|
case op_is_final:
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
* Copyright (c) 2012, 2014 Google, Inc and others.
|
* Copyright (c) 2012, 2016 Google, Inc and others.
|
||||||
* All rights reserved. This program and the accompanying materials
|
* All rights reserved. This program and the accompanying materials
|
||||||
* are made available under the terms of the Eclipse Public License v1.0
|
* are made available under the terms of the Eclipse Public License v1.0
|
||||||
* which accompanies this distribution, and is available at
|
* which accompanies this distribution, and is available at
|
||||||
|
@ -152,6 +152,47 @@ public class TypeTraits {
|
||||||
return isTrivial((ICPPClassType) type, point);
|
return isTrivial((ICPPClassType) type, point);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns true if the given type is a class type, but not a union type, with no non-static
|
||||||
|
* data members other than bit-fields of length 0, no virtual member functions, no virtual
|
||||||
|
* base classes, and no base class for which isEmpty is false. [meta.unary.prop]
|
||||||
|
*/
|
||||||
|
public static boolean isEmpty(IType type, IASTNode point) {
|
||||||
|
type = SemanticUtil.getNestedType(type, CVTYPE | TDEF);
|
||||||
|
if (!(type instanceof ICPPClassType))
|
||||||
|
return false;
|
||||||
|
ICPPClassType classType = (ICPPClassType) type;
|
||||||
|
if (!isItselfEmpty(classType, point))
|
||||||
|
return false;
|
||||||
|
ICPPClassType[] baseClasses = ClassTypeHelper.getAllBases(classType, point);
|
||||||
|
for (ICPPClassType baseClass : baseClasses) {
|
||||||
|
if (!isItselfEmpty(baseClass, point))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static boolean isItselfEmpty(ICPPClassType classType, IASTNode point) {
|
||||||
|
ICPPField[] fields = ClassTypeHelper.getDeclaredFields(classType, point);
|
||||||
|
for (ICPPField field : fields) {
|
||||||
|
if (!field.isStatic()) {
|
||||||
|
// TODO(sprigogin): Check for empty bit fields when bit field size becomes available.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ICPPMethod[] methods = ClassTypeHelper.getDeclaredMethods(classType, point);
|
||||||
|
for (ICPPMethod method : methods) {
|
||||||
|
if (method.isVirtual())
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
ICPPBase[] bases = ClassTypeHelper.getBases(classType, point);
|
||||||
|
for (ICPPBase base : bases) {
|
||||||
|
if (base.isVirtual())
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 8.5.1 Aggregates [dcl.init.aggr]
|
* 8.5.1 Aggregates [dcl.init.aggr]
|
||||||
* An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1),
|
* An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1),
|
||||||
|
|
Loading…
Add table
Reference in a new issue