/*******************************************************************************
* Copyright (c) 2007, 2008 Symbian Software Systems 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:
* Andrew Ferguson (Symbian) - Initial implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/
package org.eclipse.cdt.internal.index.tests;
import java.io.IOException;
import junit.framework.TestSuite;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.ICompositeType;
import org.eclipse.cdt.core.dom.ast.IEnumeration;
import org.eclipse.cdt.core.dom.ast.IEnumerator;
import org.eclipse.cdt.core.dom.ast.IFunction;
import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IPointerType;
import org.eclipse.cdt.core.dom.ast.ITypedef;
import org.eclipse.cdt.core.dom.ast.IValue;
import org.eclipse.cdt.core.dom.ast.IVariable;
/**
* For testing PDOM binding C language resolution
*/
/*
* aftodo - once we have non-problem bindings working, each test should
* additionally check that the binding obtained has characteristics as
* expected (type,name,etc..)
*/
public class IndexCBindingResolutionTest extends IndexBindingResolutionTestBase {
public static class SingleProject extends IndexCBindingResolutionTest {
public SingleProject() {setStrategy(new SinglePDOMTestStrategy(false));}
public static TestSuite suite() {return suite(SingleProject.class);}
}
public static class ProjectWithDepProj extends IndexCBindingResolutionTest {
public ProjectWithDepProj() {setStrategy(new ReferencedProject(false));}
public static TestSuite suite() {return suite(ProjectWithDepProj.class);}
}
public static void addTests(TestSuite suite) {
suite.addTest(SingleProject.suite());
suite.addTest(ProjectWithDepProj.suite());
}
public IndexCBindingResolutionTest() {
setStrategy(new SinglePDOMTestStrategy(false));
}
// int (*f)(int);
// int g(int n){return n;}
// void foo() {
// f= g;
// }
public void testPointerToFunction() throws Exception {
IBinding b0 = getBindingFromASTName("f= g;", 1);
IBinding b1 = getBindingFromASTName("g;", 1);
assertInstance(b0, IVariable.class);
IVariable v0= (IVariable) b0;
assertInstance(v0.getType(), IPointerType.class);
IPointerType p0= (IPointerType) v0.getType();
assertInstance(p0.getType(), IFunctionType.class);
IFunctionType f0= (IFunctionType) p0.getType();
assertInstance(f0.getReturnType(), IBasicType.class);
assertEquals(1, f0.getParameterTypes().length);
assertInstance(f0.getParameterTypes()[0], IBasicType.class);
assertInstance(b1, IFunction.class);
IFunctionType f1= ((IFunction)b1).getType();
assertInstance(f1.getReturnType(), IBasicType.class);
assertEquals(1, f1.getParameterTypes().length);
assertInstance(f1.getParameterTypes()[0], IBasicType.class);
}
// // header file
// struct S {int x;};
// union U {int x;};
// enum E {ER1,ER2,ER3};
// void func1(enum E e) {}
// void func2(struct S s) {}
// void func3(int** ppi) {}
// void func4(int n) {}
//
// int var1;
// struct S var2;
// struct S *var3;
// typedef int Int;
// typedef int *IntPtr;
// // referencing file
// void references() {
// struct S s; /*s*/
// union U u; /*u*/
// enum E e; /*e*/
// Int a; /*a*/
// IntPtr b = &a; /*b*/
// func3(&b); /*func4*/
// func4(a); /*func5*/
//
// var1 = 1; /*var1*/
// var2 = s; /*var2*/
// var3 = &s; /*var3*/
// func1(e); /*func1*/
// func1(var1); /*func2*/
// func2(s); /*func3*/
// }
public void testSimpleGlobalBindings() throws IOException {
IBinding b2 = getBindingFromASTName("S s;", 1);
IBinding b3 = getBindingFromASTName("s;", 1);
IBinding b4 = getBindingFromASTName("U u;", 1);
IBinding b5 = getBindingFromASTName("u; ", 1);
IBinding b6 = getBindingFromASTName("E e; ", 1);
IBinding b7 = getBindingFromASTName("e; ", 1);
IBinding b8 = getBindingFromASTName("var1 = 1;", 4);
IBinding b9 = getBindingFromASTName("var2 = s;", 4);
IBinding b10 = getBindingFromASTName("var3 = &s;", 4);
IBinding b11 = getBindingFromASTName("func1(e);", 5);
IBinding b12 = getBindingFromASTName("func1(var1);", 5);
IBinding b13 = getBindingFromASTName("func2(s);", 5);
IBinding b14 = getBindingFromASTName("Int a; ", 3);
IBinding b15 = getBindingFromASTName("a; ", 1);
IBinding b16 = getBindingFromASTName("IntPtr b = &a; ", 6);
IBinding b17 = getBindingFromASTName("b = &a; /*b*/", 1);
IBinding b18 = getBindingFromASTName("func3(&b);", 5);
IBinding b19 = getBindingFromASTName("b); /*func4*/", 1);
IBinding b20 = getBindingFromASTName("func4(a);", 5);
IBinding b21 = getBindingFromASTName("a); /*func5*/", 1);
}
// // empty
// typedef struct S {int a;} S;
// typedef enum E {A,B} E;
// struct A {
// S *s;
// E *e;
// };
public void testTypedefA() throws Exception {
IBinding b1 = getBindingFromASTName("S {", 1);
IBinding b2 = getBindingFromASTName("S;", 1);
IBinding b3 = getBindingFromASTName("E {", 1);
IBinding b4 = getBindingFromASTName("E;", 1);
IBinding b5 = getBindingFromASTName("S *s", 1);
IBinding b6 = getBindingFromASTName("E *e", 1);
assertInstance(b1, ICompositeType.class);
assertInstance(b2, ITypedef.class);
assertInstance(b3, IEnumeration.class);
assertInstance(b4, ITypedef.class);
assertInstance(b5, ITypedef.class);
ITypedef t5= (ITypedef) b5;
assertInstance(t5.getType(), ICompositeType.class);
assertEquals(ICompositeType.k_struct, ((ICompositeType)t5.getType()).getKey());
assertInstance(b6, ITypedef.class);
ITypedef t6= (ITypedef) b6;
assertInstance(t6.getType(), IEnumeration.class);
}
// typedef struct S {int a;} S;
// typedef enum E {A,B} E;
// struct A {
// S *s;
// E *e;
// };
public void testTypedefB() throws Exception {
IBinding b1 = getBindingFromASTName("S *s", 1);
IBinding b2 = getBindingFromASTName("E *e", 1);
assertInstance(b1, ITypedef.class);
ITypedef t1= (ITypedef) b1;
assertInstance(t1.getType(), ICompositeType.class);
assertEquals(ICompositeType.k_struct, ((ICompositeType)t1.getType()).getKey());
assertInstance(b2, ITypedef.class);
ITypedef t2= (ITypedef) b2;
assertInstance(t2.getType(), IEnumeration.class);
}
// union U {
// int x;
// int y;
// };
// struct S {
// union U u;
// int z;
// };
// typedef struct S TS;
// void refs() {
// union U b1;
// struct S b2;
// union U *b3 = &b1;
// struct S *b4 = &b2;
// TS b5;
// TS *b6 = &b5;
//
// b1.x = 0;
// b1.y = 1;
// b2.u.x = 2;
// b2.u.y = 3;
// b3->x = 4;
// b3->y = 5;
// b4->u.x = 6;
// b4->u.y = 7;
// b4->z = 8;
// b5.u.x = 9;
// b5.u.y = 10;
// b6->u.x = 11;
// b6->u.y = 12;
// b6->z = 13;
// }
public void testFieldReference() throws Exception {
IBinding b01 = getBindingFromASTName("b1;",2);
assertVariable(b01, "b1", ICompositeType.class, "U");
IBinding b02 = getBindingFromASTName("b2;",2);
assertVariable(b02, "b2", ICompositeType.class, "S");
IBinding b03 = getBindingFromASTName("b3 =",2);
assertVariable(b03, "b3", IPointerType.class, null);
assertTypeContainer(((IVariable)b03).getType(), null, IPointerType.class, ICompositeType.class, "U");
IBinding b04 = getBindingFromASTName("b4 =",2);
assertVariable(b04, "b4", IPointerType.class, null);
assertTypeContainer(((IVariable)b04).getType(), null, IPointerType.class, ICompositeType.class, "S");
IBinding b05 = getBindingFromASTName("b5;",2);
assertVariable(b05, "b5", ITypedef.class, null);
assertTypeContainer(((IVariable)b05).getType(), null, ITypedef.class, ICompositeType.class, "S");
IBinding b06 = getBindingFromASTName("b6 =",2);
assertVariable(b06, "b6", IPointerType.class, null);
assertTypeContainer(((IVariable)b06).getType(), null, IPointerType.class, ITypedef.class, "TS");
assertTypeContainer(((IPointerType)((IVariable)b06).getType()).getType(), null, ITypedef.class, ICompositeType.class, "S");
IBinding b07 = getBindingFromASTName("x = 0",1);
assertVariable(b07, "x", IBasicType.class, null);
IBinding b08 = getBindingFromASTName("y = 1",1);
assertVariable(b08, "y", IBasicType.class, null);
IBinding b09 = getBindingFromASTName("x = 0",1);
assertVariable(b09, "x", IBasicType.class, null);
IBinding b10 = getBindingFromASTName("y = 1",1);
assertVariable(b08, "y", IBasicType.class, null);
IBinding b11 = getBindingFromASTName("u.x = 2",1);
assertVariable(b11, "u", ICompositeType.class, "U");
IBinding b12 = getBindingFromASTName("x = 2",1);
assertVariable(b12, "x", IBasicType.class, null);
IBinding b13 = getBindingFromASTName("u.y = 3",1);
assertVariable(b13, "u", ICompositeType.class, "U");
IBinding b14 = getBindingFromASTName("y = 3",1);
assertVariable(b08, "y", IBasicType.class, null);
IBinding b15 = getBindingFromASTName("x = 4",1);
assertVariable(b15, "x", IBasicType.class, null);
IBinding b16 = getBindingFromASTName("y = 5",1);
assertVariable(b16, "y", IBasicType.class, null);
IBinding b17 = getBindingFromASTName("u.x = 6",1);
assertVariable(b17, "u", ICompositeType.class, "U");
IBinding b18 = getBindingFromASTName("x = 6",1);
assertVariable(b18, "x", IBasicType.class, null);
IBinding b19 = getBindingFromASTName("u.y = 7",1);
assertVariable(b19, "u", ICompositeType.class, "U");
IBinding b20 = getBindingFromASTName("y = 7",1);
assertVariable(b20, "y", IBasicType.class, null);
IBinding b21 = getBindingFromASTName("z = 8",1);
assertVariable(b21, "z", IBasicType.class, null);
IBinding b22 = getBindingFromASTName("x = 9",1);
assertVariable(b22, "x", IBasicType.class, null);
IBinding b23 = getBindingFromASTName("y = 10",1);
assertVariable(b23, "y", IBasicType.class, null);
IBinding b24 = getBindingFromASTName("u.x = 11",1);
assertVariable(b24, "u", ICompositeType.class, "U");
IBinding b25 = getBindingFromASTName("x = 11",1);
assertVariable(b25, "x", IBasicType.class, null);
IBinding b26 = getBindingFromASTName("u.y = 12",1);
assertVariable(b26, "u", ICompositeType.class, "U");
IBinding b27 = getBindingFromASTName("y = 12",1);
assertVariable(b27, "y", IBasicType.class, null);
IBinding b28 = getBindingFromASTName("z = 13",1);
assertVariable(b28, "z", IBasicType.class, null);
}
// // header file
// struct S {struct S* sp;};
// struct S foo1(struct S s);
// struct S* foo2(struct S* s);
// int foo3(int i);
// int foo4(int i, struct S s);
// // referencing content
// void references() {
// struct S s, *sp;
// foo1/*a*/(sp[1]); // IASTArraySubscriptExpression
// foo2/*b*/(sp+1); // IASTBinaryExpression
// foo2/*c*/((struct S*) sp);/*1*/ // IASTCastExpression
// foo1/*d*/(1==1 ? s : s);/*2*/ // IASTConditionalExpression
// foo4/*e*/(5, s);/*3*/ // IASTExpressionList
// foo2/*f*/(s.sp);/*4*/ foo2(sp->sp);/*5*/// IASTFieldReference
// foo1/*g*/(foo1(s));/*6*/ // IASTFunctionCallExpression
// foo1/*h*/(s);/*7*/ // IASTIdExpression
// foo3/*i*/(23489); // IASTLiteralExpression
// foo3/*j*/(sizeof(struct S));/*8*/ // IASTTypeIdExpression
// foo1/*k*/(*sp);/*9*/ // IASTUnaryExpression
// }
public void testExpressionKindForFunctionCalls() {
IBinding b0 = getBindingFromASTName("foo1/*a*/", 4);
IBinding b0a = getBindingFromASTName("sp[1]", 2);
IBinding b1 = getBindingFromASTName("foo2/*b*/", 4);
IBinding b1a = getBindingFromASTName("sp+1);", 2);
IBinding b2 = getBindingFromASTName("foo2/*c*/", 4);
IBinding b2a = getBindingFromASTName("sp);/*1*/", 2);
IBinding b3 = getBindingFromASTName("foo1/*d*/", 4);
IBinding b3a = getBindingFromASTName("s : s);/*2*/", 1);
IBinding b3b = getBindingFromASTName("s);/*2*/", 1);
IBinding b4 = getBindingFromASTName("foo4/*e*/", 4);
IBinding b4a = getBindingFromASTName("s);/*3*/", 1);
IBinding b5 = getBindingFromASTName("foo2/*f*/", 4);
IBinding b5a = getBindingFromASTName("s.sp);/*4*/", 1);
IBinding b5b = getBindingFromASTName("sp);/*4*/", 2);
IBinding b5c = getBindingFromASTName("sp->sp);/*5*/", 2);
IBinding b5d = getBindingFromASTName("sp);/*5*/", 2);
IBinding b6 = getBindingFromASTName("foo1/*g*/", 4);
IBinding b6a = getBindingFromASTName("foo1(s));/*6*/", 4);
IBinding b6b = getBindingFromASTName("s));/*6*/", 1);
IBinding b7 = getBindingFromASTName("foo1/*h*/", 4);
IBinding b7a = getBindingFromASTName("s);/*7*/", 1);
IBinding b8 = getBindingFromASTName("foo3/*i*/", 4);
IBinding b9 = getBindingFromASTName("foo3/*j*/", 4);
IBinding b9a = getBindingFromASTName("S));/*8*/", 1);
IBinding b10 = getBindingFromASTName("foo1/*k*/", 4);
IBinding b10a = getBindingFromASTName("sp);/*9*/ ", 2);
}
// // header file
// struct myStruct {
// int a;
// };
// union myUnion {
// int b;
// };
// // referencing content
// struct myStruct;
// union myUnion;
// void test() {
// struct myStruct* u;
// union myUnion* v;
// u->a= 1; // since we include the definition, we may use the type.
// v->b= 1; // since we include the definition, we may use the type.
// }
public void testTypeDefinitionWithFwdDeclaration() {
getBindingFromASTName("a= 1", 1);
getBindingFromASTName("b= 1", 1);
}
// int a= 1+2-3*4+10/2; // -4
// int b= a+4;
// int* c= &b;
// enum X {e0, e4=4, e5, e2=2, e3};
// void ref() {
// a; b; c; e0; e2; e3; e4; e5;
// }
public void testValues() throws Exception {
IVariable v= (IVariable) getBindingFromASTName("a;", 1);
checkValue(v.getInitialValue(), -4);
v= (IVariable) getBindingFromASTName("b;", 1);
checkValue(v.getInitialValue(), 0);
v= (IVariable) getBindingFromASTName("c;", 1);
assertNull(v.getInitialValue().numericalValue());
IEnumerator e= (IEnumerator) getBindingFromASTName("e0", 2);
checkValue(e.getValue(), 0);
e= (IEnumerator) getBindingFromASTName("e2", 2);
checkValue(e.getValue(), 2);
e= (IEnumerator) getBindingFromASTName("e3", 2);
checkValue(e.getValue(), 3);
e= (IEnumerator) getBindingFromASTName("e4", 2);
checkValue(e.getValue(), 4);
e= (IEnumerator) getBindingFromASTName("e5", 2);
checkValue(e.getValue(), 5);
}
private void checkValue(IValue initialValue, int i) {
assertNotNull(initialValue);
final Long numericalValue = initialValue.numericalValue();
assertNotNull(numericalValue);
assertEquals(i, numericalValue.intValue());
}
}