1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-07-26 18:35:32 +02:00

Bug 280909: Syntax and bindings for variadic templates.

This commit is contained in:
Markus Schorn 2009-12-18 09:58:29 +00:00
parent 2a9515f36d
commit 6ad255dfed
108 changed files with 3490 additions and 1547 deletions

View file

@ -487,6 +487,8 @@ public class AST2BaseTest extends BaseTestCase {
} }
public IBinding assertProblem(String section, int len) { public IBinding assertProblem(String section, int len) {
if (len <= 0)
len= section.length()-len;
IBinding binding= binding(section, len); IBinding binding= binding(section, len);
assertTrue("Non-ProblemBinding for name: " + section.substring(0, len), assertTrue("Non-ProblemBinding for name: " + section.substring(0, len),
binding instanceof IProblemBinding); binding instanceof IProblemBinding);
@ -494,6 +496,8 @@ public class AST2BaseTest extends BaseTestCase {
} }
public <T extends IBinding> T assertNonProblem(String section, int len) { public <T extends IBinding> T assertNonProblem(String section, int len) {
if (len <= 0)
len= section.length()-len;
IBinding binding= binding(section, len); IBinding binding= binding(section, len);
if (binding instanceof IProblemBinding) { if (binding instanceof IProblemBinding) {
IProblemBinding problem= (IProblemBinding) binding; IProblemBinding problem= (IProblemBinding) binding;

View file

@ -4343,4 +4343,364 @@ public class AST2TemplateTests extends AST2BaseTest {
ICPPTemplateInstance inst= bh.assertNonProblem("f(i)", 1); ICPPTemplateInstance inst= bh.assertNonProblem("f(i)", 1);
assertEquals("<int &>", ASTTypeUtil.getArgumentListString(inst.getTemplateArguments(), true)); assertEquals("<int &>", ASTTypeUtil.getArgumentListString(inst.getTemplateArguments(), true));
} }
// template<typename... Pack> void f1(int (* p)(Pack ...a));
// template<typename... Pack> void f2(int (* ...p)(Pack a, int));
// template<typename... Pack> void f3(Pack (* ...p)());
// template<int... ipack> void f4(int (&...p)[ipack]);
// template<typename... Pack> void f5(Pack ...);
// template<typename NonPack> void f6(NonPack ...);
// template<typename... T> void f7() throw(T...);
public void testFunctionParameterPacks_280909() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ICPPFunctionTemplate f= bh.assertNonProblem("f1", 2);
assertEquals("void (int (*)(#0 ...))", ASTTypeUtil.getType(f.getType(), true));
assertFalse(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f2", 2);
assertEquals("void (int (* ...)(#0, int))", ASTTypeUtil.getType(f.getType(), true));
assertTrue(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f3", 2);
assertEquals("void (#0 (* ...)())", ASTTypeUtil.getType(f.getType(), true));
assertTrue(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f4", 2);
assertEquals("void (int (& ...)[#0])", ASTTypeUtil.getType(f.getType(), true));
assertTrue(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f5", 2);
assertEquals("void (#0 ...)", ASTTypeUtil.getType(f.getType(), true));
assertTrue(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f6", 2);
assertEquals("void (#0, ...)", ASTTypeUtil.getType(f.getType(), true));
assertFalse(f.getParameters()[0].isParameterPack());
f= bh.assertNonProblem("f7", 2);
assertEquals("#0 ...", ASTTypeUtil.getType(f.getExceptionSpecification()[0], true));
}
// template<typename... Pack> class C1 {};
// template<template<typename... NP> class... Pack> class C2 {};
// template<int... Pack> class C3 {};
public void testTemplateParameterPacks_280909() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ICPPClassTemplate ct= bh.assertNonProblem("C1", 2);
ICPPTemplateParameter tp= ct.getTemplateParameters()[0];
assertTrue(tp.isParameterPack());
ct= bh.assertNonProblem("C2", 2);
tp= ct.getTemplateParameters()[0];
assertTrue(tp.isParameterPack());
ct= bh.assertNonProblem("C3", 2);
tp= ct.getTemplateParameters()[0];
assertTrue(tp.isParameterPack());
}
// template<typename... T> void f1(T*...);
// template<typename T> void f2(T*...);
public void testTemplateParameterPacksAmbiguity_280909() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ICPPFunctionTemplate ft= bh.assertNonProblem("f1", 2);
ICPPTemplateParameter tp= ft.getTemplateParameters()[0];
assertTrue(tp.isParameterPack());
ft= bh.assertNonProblem("f2", 2);
tp= ft.getTemplateParameters()[0];
assertFalse(tp.isParameterPack());
}
// template<typename... Types>
// struct count { static const int value = sizeof...(Types);
// };
public void testVariadicTemplateExamples_280909a() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename... T> void f(T (* ...t)(int, int));
// int add(int, int);
// float subtract(int, int);
// void g() {
// f(add, subtract);
// }
public void _testVariadicTemplateExamples_280909b() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename... Mixins>
// class X : public Mixins...
// {public:
// X(const Mixins&... mixins) : Mixins(mixins)... { }
// };
public void testVariadicTemplateExamples_280909c() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<class... Types> class Tuple; // Types is a template type parameter pack
// template<class T, int... Dims> struct multi array; // Dims is a non-type template parameter pack
public void testVariadicTemplateExamples_280909d() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<class T = char> class String;
// String<>* p; // OK: String<char>
// String* q; // syntax error
// template<typename ... Elements> class Tuple;
// Tuple<>* t; // OK: Elements is empty
// Tuple* u; // syntax error
public void testVariadicTemplateExamples_280909e() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("String<>", 6);
bh.assertProblem("String*", 6);
bh.assertNonProblem("Tuple<>", 5);
bh.assertProblem("Tuple*", 5);
}
// template<class T> class A {};
// template<class T, class U = T> class B {};
// template<class... Types> class C {};
// template<template<class> class P> class X {};
// template<template<class...> class Q> class Y {};
// X<A> xa; // okay
// X<B> xb; // ill-formed: default arguments for the parameters of a template template argument are ignored
// X<C> xc; // ill-formed: a template parameter pack does not match a template parameter
// Y<A> ya; // ill-formed: a template parameter pack does not match a template parameter
// Y<B> yb; // ill-formed: a template parameter pack does not match a template parameter
// Y<C> yc; // okay
public void _testVariadicTemplateExamples_280909f() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("X<A>", 4);
bh.assertProblem("X<B>", 4);
bh.assertProblem("X<C>", 4);
bh.assertProblem("Y<A>", 4);
bh.assertProblem("Y<B>", 4);
bh.assertNonProblem("Y<C>", 4);
}
// template<class T1, class T2> struct A {
// void f1();
// void f2();
// };
// template<class... Types> struct B {
// void f3();
// void f4();
// };
// template<class T2, class T1> void A<T2,T1>::f1() {} // OK
// template<class T2, class T1> void A<T1,T2>::f2() {} // error
// template<class... Types> void B<Types...>::f3() {} // OK
// template<class... Types> void B<Types>::f4() {} // error
public void testVariadicTemplateExamples_280909g() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("f1() {}", 2);
bh.assertProblem("f2() {}", 2);
bh.assertNonProblem("f3() {}", 2);
bh.assertProblem("f4() {}", 2);
}
// template<class X, class Y> X f(Y);
// template<class X, class Y, class... Z> X g(Y);
// void gh() {
// int i = f<int>(5.6); // Y is deduced to be double
// int j = f(5.6); // ill-formed: X cannot be deduced
// f<void>(f<int, bool>); // Y for outer f deduced to be
// // int (*)(bool)
// f<void>(f<int>); // ill-formed: f<int> does not denote a
// // single function template specialization
// int k = g<int>(5.6); // Y is deduced to be double, Z is deduced to an empty sequence
// f<void>(g<int, bool>); // Y for outer f deduced to be
// } // int (*)(bool), Z is deduced to an empty sequence
public void _testVariadicTemplateExamples_280909h() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("f<int>(5.6)", 6);
bh.assertProblem("f(5.6)", 1);
bh.assertNonProblem("f<void>(f<int, bool>)", 7);
bh.assertProblem("f<void>(f<int>)", 7);
bh.assertNonProblem("g<int>(5.6)", 6);
bh.assertNonProblem("f<void>(g<int, bool>)", 7);
}
// template<class X, class Y, class Z> X f(Y,Z);
// template<class... Args> void f2();
// void g() {
// f<int,char*,double>("aa",3.0);
// f<int,char*>("aa",3.0); // Z is deduced to be double
// f<int>("aa",3.0); // Y is deduced to be const char*, and
// // Z is deduced to be double
// f("aa",3.0); // error: X cannot be deduced
// f2<char, short, int, long>(); // okay
// }
public void _testVariadicTemplateExamples_280909i() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("f<int,char*,double>", 0);
bh.assertNonProblem("f<int,char*>", 0);
bh.assertProblem("f<int>", 0);
bh.assertNonProblem("f(", 1);
bh.assertNonProblem("f2<char, short, int, long>", 0);
}
// template<typename... Types> void f(Types... values);
// void g() {
// f<int*, float*>(0, 0, 0); // Types is the sequence int*, float*, int
// }
public void _testVariadicTemplateExamples_280909j() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<class... Types> void f(Types&...);
// template<class T, class... Types> void g(T1, Types...);
// void h(int x, float& y) {
// const int z = x;
// f(x, y, z); // Types is deduced to int, float, const int
// g(x, y, z); // T1 is deduced to int, Types is deduced to float, int
// }
public void _testVariadicTemplateExamples_280909k() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename...> struct Tuple { };
// template<typename... Types> void g(Tuple<Types...>); // #1
// template<typename T1, typename... Types> void g(Tuple<T1, Types...>); // #2
// template<typename T1, typename... Types> void g(Tuple<T1, Types&...>); // #3
// g(Tuple<>()); // calls #1
// g(Tuple<int, float>()); // calls #2
// g(Tuple<int, float&>()); // calls #3
// g(Tuple<int>()); // calls #3
public void _testVariadicTemplateExamples_280909m() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ICPPFunction g1= bh.assertNonProblem("g(Tuple<Types...>)", 1);
ICPPFunction g2= bh.assertNonProblem("g(Tuple<T1, Types...>)", 1);
ICPPFunction g3= bh.assertNonProblem("g(Tuple<T1, Types&...>)", 1);
ICPPFunction x= bh.assertNonProblem("g(Tuple<>())", 1);
assertSame(g1, x);
x= bh.assertNonProblem("g(Tuple<int, float>())", 1);
assertSame(g2, x);
x= bh.assertNonProblem("g(Tuple<int, float&>())", 1);
assertSame(g3, x);
x= bh.assertNonProblem("g(Tuple<int>())", 1);
assertSame(g3, x);
}
// template<class> struct X { };
// template<class R, class... ArgTypes> struct X<R(int, ArgTypes...)> { };
// template<class... Types> struct Y { };
// template<class T, class... Types> struct Y<T, Types&...> { };
// template <class... Types> int f (void ()(Types...));
// void g(int, float);
// X<int> x1; // uses primary template
// X<int(int, float, double)> x2; // uses partial specialization, ArgTypes contains float, double
// X<int(float, int)> x3; // uses primary template
// Y<> y1; // uses primary template, Types is empty
// Y<int&, float&, double&> y2; // uses partial specialization. T is int&, Types contains float, double
// Y<int, float, double> y3; // uses primary template, Types contains int, float, double
// int fv = f(g); // okay, Types contains int, float
public void _testVariadicTemplateExamples_280909n() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename... Args> void f(Args... args); // #1
// template<typename T1, typename... Args> void f(T1 a1, Args... args); // #2
// template<typename T1, typename T2> void f(T1 a2, T2 a2); // #3
// void test() {
// f(); // calls #1
// f(1, 2, 3); // calls #2
// f(1, 2); // calls #3; non-variadic template #3 is
// } // more specialized than the variadic templates #1 and #2
public void _testVariadicTemplateExamples_280909o() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ICPPFunction f1= bh.assertNonProblem("f(Args... args)", 1);
ICPPFunction f2= bh.assertNonProblem("f(T1 a1, Args... args)", 1);
ICPPFunction f3= bh.assertNonProblem("f(T1 a2, T2 a2)", 1);
ICPPFunction x= bh.assertNonProblem("f()", 1);
assertSame(f1, x);
x= bh.assertNonProblem("f(1, 2, 3)", 1);
assertSame(f2, x);
x= bh.assertNonProblem("f(1, 2)", 1);
assertSame(f3, x);
}
// template<typename... Types> struct Tuple { };
// void test() {
// Tuple<> t0; // Types contains no arguments
// Tuple<int> t1; // Types contains one argument: int
// Tuple<int, float> t2; // Types contains two arguments: int and float
// Tuple<0> error; // Error: 0 is not a type
// }
public void _testVariadicTemplateExamples_280909p() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("Tuple<>", 0);
bh.assertNonProblem("Tuple<int>", 0);
bh.assertNonProblem("Tuple<int, float>", 0);
bh.assertProblem("Tuple<0>", 0);
}
// template<typename... Types> void f(Types... args);
// void test() {
// f(); // okay: args contains no arguments
// f(1); // okay: args contains one int argument
// f(2, 1.0); // okay: args contains two arguments, an int and a double
// }
public void _testVariadicTemplateExamples_280909q() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename... Types> void f(Types... rest);
// template<typename... Types> void g(Types... rest) {
// f(&rest...); // &rest... is a pack expansion, &rest is its pattern
// }
public void testVariadicTemplateExamples_280909r() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// template<typename...> struct Tuple {};
// template<typename T1, typename T2> struct Pair {};
// template<typename... Args1> struct zip {
// template<typename... Args2> struct with {
// typedef Tuple<Pair<Args1, Args2>...> type;
// };
// };
// typedef zip<short, int>::with<unsigned short, unsigned>::type T1;
// // T1 is Tuple<Pair<short, unsigned short>, Pair<int, unsigned> >
// typedef zip<short>::with<unsigned short, unsigned>::type T2;
// // error: different number of arguments specified
// // for Args1 and Args2
// template<typename... Args> void g(Args... args) {
// f(const cast<const Args*>(&args)...); // okay: Args and args are expanded
// f(5 ...); // error: pattern does not contain any parameter packs
// f(args); // error: parameter pack args is not expanded
// f(h(args...) + args...); // okay: first args expanded within h, second args expanded within f.
// }
public void _testVariadicTemplateExamples_280909s() throws Exception {
final String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, true);
ITypedef td= bh.assertNonProblem("T1;", 2);
assertEquals("Tuple<Pair<short, unsigned short>, Pair<int, unsigned> >", ASTTypeUtil.getType(td, true));
bh.assertProblem("zip<short>::with<unsigned short, unsigned>::type", 0);
bh.assertNonProblem("f(const cast<const Args*>(&args)...)", 1);
bh.assertProblem("f(5 ...)", 1);
bh.assertProblem("f(args)", 1);
bh.assertNonProblem("f(h(args...) + args...)", 1);
}
} }

View file

@ -44,6 +44,7 @@ import org.eclipse.cdt.core.dom.ast.c.ICASTPointer;
import org.eclipse.cdt.core.dom.ast.c.ICASTSimpleDeclSpecifier; import org.eclipse.cdt.core.dom.ast.c.ICASTSimpleDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
@ -55,12 +56,13 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTSimpleTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression;
import org.eclipse.cdt.core.dom.ast.gnu.c.ICASTKnRFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.gnu.c.ICASTKnRFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTPointer; import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTPointer;
import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTSimpleDeclSpecifier; import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTSimpleDeclSpecifier;
import org.eclipse.cdt.core.parser.Keywords; import org.eclipse.cdt.core.parser.Keywords;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
/** /**
@ -129,7 +131,7 @@ public class ASTStringUtil {
*/ */
public static String getReturnTypeString(IASTDeclSpecifier declSpecifier, IASTFunctionDeclarator fdecl) { public static String getReturnTypeString(IASTDeclSpecifier declSpecifier, IASTFunctionDeclarator fdecl) {
final StringBuilder buffer= new StringBuilder(); final StringBuilder buffer= new StringBuilder();
final IASTDeclarator declarator= CPPVisitor.findOutermostDeclarator(fdecl); final IASTDeclarator declarator= ASTQueries.findOutermostDeclarator(fdecl);
appendDeclarationString(buffer, declSpecifier, declarator, fdecl); appendDeclarationString(buffer, declSpecifier, declarator, fdecl);
return trimRight(buffer).toString(); return trimRight(buffer).toString();
} }
@ -273,6 +275,8 @@ public class ASTStringUtil {
|| declarator instanceof IASTFunctionDeclarator || declarator instanceof IASTFunctionDeclarator
|| declarator instanceof IASTFieldDeclarator; || declarator instanceof IASTFieldDeclarator;
appendDeclaratorString(buffer, nestedDeclarator, protectPointers, returnTypeOf); appendDeclaratorString(buffer, nestedDeclarator, protectPointers, returnTypeOf);
} else if (declarator instanceof ICPPASTDeclarator && ((ICPPASTDeclarator) declarator).declaresParameterPack()) {
buffer.append(Keywords.cpELLIPSIS);
} }
if (declarator instanceof IASTArrayDeclarator) { if (declarator instanceof IASTArrayDeclarator) {
@ -359,6 +363,8 @@ public class ASTStringUtil {
private static StringBuilder appendTypeIdString(StringBuilder buffer, IASTTypeId typeId) { private static StringBuilder appendTypeIdString(StringBuilder buffer, IASTTypeId typeId) {
appendDeclSpecifierString(buffer, typeId.getDeclSpecifier()); appendDeclSpecifierString(buffer, typeId.getDeclSpecifier());
appendDeclaratorString(buffer, typeId.getAbstractDeclarator(), false, null); appendDeclaratorString(buffer, typeId.getAbstractDeclarator(), false, null);
if (typeId instanceof ICPPASTTypeId && ((ICPPASTTypeId) typeId).isPackExpansion())
buffer.append(Keywords.cpELLIPSIS);
return buffer; return buffer;
} }

View file

@ -11,8 +11,6 @@
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast; package org.eclipse.cdt.core.dom.ast;
import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.TDEF;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.LinkedList; import java.util.LinkedList;
@ -27,6 +25,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPBinding;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
@ -70,13 +69,20 @@ public class ASTTypeUtil {
String[] parms = getParameterTypeStringArray(type); String[] parms = getParameterTypeStringArray(type);
result.append(Keywords.cpLPAREN); result.append(Keywords.cpLPAREN);
for (int i = 0; i < parms.length; i++) { boolean needComma= false;
if (parms[i] != null) { for (String parm : parms) {
result.append(parms[i]); if (parm != null) {
if (i < parms.length - 1) if (needComma)
result.append(COMMA_SPACE); result.append(COMMA_SPACE);
result.append(parm);
needComma= true;
} }
} }
if (type instanceof ICPPFunctionType && ((ICPPFunctionType) type).takesVarArgs()) {
if (needComma)
result.append(COMMA_SPACE);
result.append(Keywords.cpELLIPSIS);
}
result.append(Keywords.cpRPAREN); result.append(Keywords.cpRPAREN);
return result.toString(); return result.toString();
} }
@ -94,16 +100,10 @@ public class ASTTypeUtil {
if (parameters.length == 0) { if (parameters.length == 0) {
return false; return false;
} else if (parameters.length == 1) { }
IType ultimateType = SemanticUtil.getNestedType(parameters[0].getType(), TDEF); if (parameters.length == 1 && SemanticUtil.isVoidType(parameters[0].getType())) {
if (ultimateType instanceof IBasicType) {
if (((IBasicType) ultimateType).getKind() == Kind.eVoid) {
return false; return false;
} }
}
}
return true; return true;
} }
@ -355,6 +355,8 @@ public class ASTTypeUtil {
} else { } else {
result.append(Keywords.cpAMPER); result.append(Keywords.cpAMPER);
} }
} else if (type instanceof ICPPParameterPackType) {
result.append(Keywords.cpELLIPSIS);
} else if (type instanceof IEnumeration) { } else if (type instanceof IEnumeration) {
result.append(Keywords.ENUM); result.append(Keywords.ENUM);
result.append(SPACE); result.append(SPACE);

View file

@ -112,6 +112,12 @@ public interface IASTUnaryExpression extends IASTExpression {
*/ */
public static final int op_alignOf = 15; public static final int op_alignOf = 15;
/**
* For c++, only: 'sizeof...(parameterPack)'
* @since 5.2
*/
public static final int op_sizeofParameterPack = 16;
/** /**
* <code>op_last</code> is made available for subclasses. * <code>op_last</code> is made available for subclasses.
* @deprecated all constants must be defined in this interface * @deprecated all constants must be defined in this interface

View file

@ -7,9 +7,11 @@
* *
* Contributors: * Contributors:
* Andrew Ferguson (Symbian) - Initial Implementation * Andrew Ferguson (Symbian) - Initial Implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTIdExpression; import org.eclipse.cdt.core.dom.ast.IASTIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
@ -25,9 +27,10 @@ public interface ICPPASTAmbiguousTemplateArgument extends IASTNode {
/** /**
* Add an partial parse tree that could be a suitable subtree representing * Add an partial parse tree that could be a suitable subtree representing
* the template argument * the template argument
* @param idExpression a non-null id-expression * @param idExpression a non-null id-expression or a pack expansion of an id-expression
* @since 5.2
*/ */
public void addIdExpression(IASTIdExpression idExpression); public void addIdExpression(IASTExpression idExpression);
/** /**
* Add an partial parse tree that could be a suitable subtree representing * Add an partial parse tree that could be a suitable subtree representing
@ -35,4 +38,10 @@ public interface ICPPASTAmbiguousTemplateArgument extends IASTNode {
* @param typeId a non-null type-id * @param typeId a non-null type-id
*/ */
public void addTypeId(IASTTypeId typeId); public void addTypeId(IASTTypeId typeId);
/**
* @deprecated Replaced by {@link #addIdExpression(IASTExpression)}.
*/
@Deprecated
public void addIdExpression(IASTIdExpression idExpression);
} }

View file

@ -0,0 +1,24 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTArrayDeclarator;
/**
* Array declarator for C++
* @since 5.2
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface ICPPASTArrayDeclarator extends IASTArrayDeclarator, ICPPASTDeclarator{
}

View file

@ -50,87 +50,56 @@ public interface ICPPASTCompositeTypeSpecifier extends IASTCompositeTypeSpecifie
/** /**
* Base Specifiers are where a class expresses from whom it inherits. * Base Specifiers are where a class expresses from whom it inherits.
* *
* @author jcamelon
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public static interface ICPPASTBaseSpecifier extends IASTNode, IASTNameOwner { public static interface ICPPASTBaseSpecifier extends IASTNode, IASTNameOwner, ICPPASTPackExpandable {
/**
* Constant.
*/
public static final ICPPASTBaseSpecifier[] EMPTY_BASESPECIFIER_ARRAY = new ICPPASTBaseSpecifier[0]; public static final ICPPASTBaseSpecifier[] EMPTY_BASESPECIFIER_ARRAY = new ICPPASTBaseSpecifier[0];
/** /**
* Is the keyword virtual used? * Relation between base specifier and its name.
*
* @return boolean
*/
public boolean isVirtual();
/**
* Set the virtual flag on/off.
*
* @param value
* boolean
*/
public void setVirtual(boolean value);
/**
* <code>v_public</code> was public keyword used in describing this
* base class?
*/
public static final int v_public = 1;
/**
* <code>v_protected</code> was protected keyword used in describing
* this base class?
*/
public static final int v_protected = 2;
/**
* <code>v_private</code> was private keyword used in describing this
* base class?
*/
public static final int v_private = 3;
/**
* Get the visibility.
*
* @return int
*/
public int getVisibility();
/**
* Set the visibility.
*
* @param visibility
*/
public void setVisibility(int visibility);
/**
* <code>NAME</code> is the name of the base class.
*/ */
public static final ASTNodeProperty NAME = new ASTNodeProperty( public static final ASTNodeProperty NAME = new ASTNodeProperty(
"ICPPASTBaseSpecifier.NAME - Name of base class"); //$NON-NLS-1$ "ICPPASTBaseSpecifier.NAME - Name of base class"); //$NON-NLS-1$
/**
* Get the name. public static final int v_public = 1;
* public static final int v_protected = 2;
* @return <code>IASTName</code> public static final int v_private = 3;
*/
public IASTName getName();
/** /**
* Set the name. * Returns whether this specifies a virtual base.
*
* @param name
* <code>IASTName</code>
*/ */
public void setName(IASTName name); public boolean isVirtual();
/**
* Returns the accessibility for the base.
*/
public int getVisibility();
/**
* Returns the name of this specifier.
*/
public IASTName getName();
/** /**
* @since 5.1 * @since 5.1
*/ */
public ICPPASTBaseSpecifier copy(); public ICPPASTBaseSpecifier copy();
/**
* Sets the name for this specifier, not allowed on frozen AST.
*/
public void setName(IASTName name);
/**
* Sets whether this specifier is for a virtual base. Not allowed on frozen AST.
*/
public void setVirtual(boolean value);
/**
* Sets the visibility of this specifier, not allowed on frozen AST.
*/
public void setVisibility(int visibility);
} }
/** /**

View file

@ -13,7 +13,6 @@ package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty; import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNameOwner; import org.eclipse.cdt.core.dom.ast.IASTNameOwner;
@ -27,7 +26,7 @@ import org.eclipse.cdt.core.dom.ast.IASTNameOwner;
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTConstructorChainInitializer extends IASTInitializer, IASTNameOwner { public interface ICPPASTConstructorChainInitializer extends ICPPASTInitializer, IASTNameOwner {
/** /**
* Constant. * Constant.
*/ */

View file

@ -7,12 +7,12 @@
* *
* Contributors: * Contributors:
* Doug Schaefer (IBM) - Initial API and implementation * Doug Schaefer (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty; import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializer;
/** /**
* This is an initializer that is a call to the constructor for the declarator. * This is an initializer that is a call to the constructor for the declarator.
@ -20,7 +20,7 @@ import org.eclipse.cdt.core.dom.ast.IASTInitializer;
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTConstructorInitializer extends IASTInitializer { public interface ICPPASTConstructorInitializer extends ICPPASTInitializer {
/** /**
* <code>EXPRESSION</code> represents the expression being conusmed in a * <code>EXPRESSION</code> represents the expression being conusmed in a

View file

@ -0,0 +1,35 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
/**
* Declarator for c++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTDeclarator extends IASTDeclarator {
/**
* Returns whether the declarator contains an ellipsis, in which case it declares a
* parameter pack.
*/
public boolean declaresParameterPack();
/**
* Set whether the declarator contains an ellipsis, denoting a pack expansion.
* Not allowed on frozen AST.
*/
public void setDeclaresParameterPack(boolean val);
}

View file

@ -0,0 +1,24 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTFieldDeclarator;
/**
* Field declarator for c++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTFieldDeclarator extends IASTFieldDeclarator, ICPPASTDeclarator {
}

View file

@ -21,7 +21,7 @@ import org.eclipse.cdt.core.dom.ast.IASTTypeId;
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
*/ */
public interface ICPPASTFunctionDeclarator extends IASTStandardFunctionDeclarator { public interface ICPPASTFunctionDeclarator extends IASTStandardFunctionDeclarator, ICPPASTDeclarator {
/** /**
* Used as return value for {@link #getExceptionSpecification()}. * Used as return value for {@link #getExceptionSpecification()}.
@ -66,6 +66,11 @@ public interface ICPPASTFunctionDeclarator extends IASTStandardFunctionDeclarato
*/ */
public void setPureVirtual(boolean isPureVirtual); public void setPureVirtual(boolean isPureVirtual);
/**
* @since 5.2
*/
public ICPPASTParameterDeclaration[] getParameters();
/** /**
* Returns an array of type-ids representing the exception specification. The return value * Returns an array of type-ids representing the exception specification. The return value
* {@link #NO_EXCEPTION_SPECIFICATION} indicates that no exceptions are specified, whereas * {@link #NO_EXCEPTION_SPECIFICATION} indicates that no exceptions are specified, whereas

View file

@ -0,0 +1,22 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTInitializer;
/**
* Initializer for c++
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTInitializer extends IASTInitializer, ICPPASTPackExpandable {}

View file

@ -0,0 +1,24 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression;
/**
* Initializer expression for c++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTInitializerExpression extends IASTInitializerExpression, ICPPASTInitializer {
}

View file

@ -0,0 +1,24 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTInitializerList;
/**
* Initializer expression for c++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTInitializerList extends IASTInitializerList, ICPPASTInitializer {
}

View file

@ -0,0 +1,32 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
/**
* Interface for nodes that can potentially be pack-expansions.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTPackExpandable {
/**
* Returns whether this base specifier is a pack expansion.
* @since 5.2
*/
public boolean isPackExpansion();
/**
* Sets whether this base specifier is a pack expansion. Not allowed on frozen AST.
* @since 5.2
*/
public void setIsPackExpansion(boolean val);
}

View file

@ -0,0 +1,40 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
/**
* Pack expansion as it can occur as an element in an expression-lists or as a
* non-type template argument.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTPackExpansionExpression extends IASTExpression {
/**
* Represents the relationship between a pack-expansion and its pattern.
*/
public static final ASTNodeProperty PATTERN = new ASTNodeProperty("ICPPASTPackExpansionExpression.Pattern [IASTExpression]"); //$NON-NLS-1$
/**
* Returns the pattern of the pack expansion.
*/
IASTExpression getPattern();
/**
* Sets the pattern of the pack expansion expression. Cannot be called on frozen ast.
*/
void setPattern(IASTExpression left);
}

View file

@ -7,6 +7,7 @@
* *
* Contributors: * Contributors:
* John Camelon (IBM) - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
@ -16,11 +17,20 @@ import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTParameterDeclaration extends ICPPASTTemplateParameter, public interface ICPPASTParameterDeclaration extends ICPPASTTemplateParameter, IASTParameterDeclaration {
IASTParameterDeclaration {
/**
* @since 5.2
*/
ICPPASTParameterDeclaration[] EMPTY_CPPPARAMETERDECLARATION_ARRAY = {};
/** /**
* @since 5.1 * @since 5.1
*/ */
public ICPPASTParameterDeclaration copy(); public ICPPASTParameterDeclaration copy();
/**
* @since 5.2
*/
public ICPPASTDeclarator getDeclarator();
} }

View file

@ -7,6 +7,7 @@
* *
* Contributors: * Contributors:
* John Camelon (IBM) - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
@ -21,8 +22,19 @@ import org.eclipse.cdt.core.dom.ast.IASTTypeId;
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTSimpleTypeTemplateParameter extends public interface ICPPASTSimpleTypeTemplateParameter extends ICPPASTTemplateParameter, IASTNameOwner {
ICPPASTTemplateParameter, IASTNameOwner {
/**
* Relation between template parameter and its name.
*/
public static final ASTNodeProperty PARAMETER_NAME = new ASTNodeProperty(
"ICPPASTSimpleTypeTemplateParameter.PARAMETER_NAME - The Parameter's Name"); //$NON-NLS-1$
/**
* Relation between template parameter and its default type.
*/
public static final ASTNodeProperty DEFAULT_TYPE = new ASTNodeProperty(
"ICPPASTSimpleTypeTemplateParameter.DEFAULT_TYPE - Optional default TypeId value"); //$NON-NLS-1$
/** /**
* <code>st_class</code> represents a class. * <code>st_class</code> represents a class.
@ -34,60 +46,40 @@ public interface ICPPASTSimpleTypeTemplateParameter extends
*/ */
public static final int st_typename = 2; public static final int st_typename = 2;
/** /**
* Get the parameter type. * Get the parameter type.
*
* @return int
*/ */
public int getParameterType(); public int getParameterType();
/** /**
* Set the parameter type. * Returns the template parameter name.
*
* @param value
* int
*/
public void setParameterType(int value);
/**
* The parameter name.
*/
public static final ASTNodeProperty PARAMETER_NAME = new ASTNodeProperty(
"ICPPASTSimpleTypeTemplateParameter.PARAMETER_NAME - The Parameter's Name"); //$NON-NLS-1$
/**
* Get the name.
*
* @return <code>IASTName</code>
*/ */
public IASTName getName(); public IASTName getName();
/** /**
* Set the name. * Returns the default value (a type id) for this template parameter, or <code>null</code>.
*
* @param name
* <code>IASTName</code>
*/
public void setName(IASTName name);
/**
* DEFAULT_TYPE is the optional default typeId value
*/
public static final ASTNodeProperty DEFAULT_TYPE = new ASTNodeProperty(
"ICPPASTSimpleTypeTemplateParameter.DEFAULT_TYPE - Optional default TypeId value"); //$NON-NLS-1$
/**
* Get the default type.
*
* @return <code>IASTTypeId</code>
*/ */
public IASTTypeId getDefaultType(); public IASTTypeId getDefaultType();
/** /**
* Set the default type. * Set the parameter type.
* */
* @param typeId public void setParameterType(int value);
* <code>IASTTypeId</code>
/**
* Set whether this is a parameter pack.
* @since 5.2
*/
public void setIsParameterPack(boolean val);
/**
* Sets the template parameter name.
*/
public void setName(IASTName name);
/**
* Sets the default value (a type id) for this template parameter.
*/ */
public void setDefaultType(IASTTypeId typeId); public void setDefaultType(IASTTypeId typeId);
@ -95,5 +87,4 @@ public interface ICPPASTSimpleTypeTemplateParameter extends
* @since 5.1 * @since 5.1
*/ */
public ICPPASTSimpleTypeTemplateParameter copy(); public ICPPASTSimpleTypeTemplateParameter copy();
} }

View file

@ -7,6 +7,7 @@
* *
* Contributors: * Contributors:
* John Camelon (IBM) - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
@ -19,11 +20,14 @@ import org.eclipse.cdt.core.dom.ast.IASTNode;
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTTemplateParameter extends IASTNode { public interface ICPPASTTemplateParameter extends IASTNode {
/**
* Constant
*/
public static final ICPPASTTemplateParameter[] EMPTY_TEMPLATEPARAMETER_ARRAY = new ICPPASTTemplateParameter[0]; public static final ICPPASTTemplateParameter[] EMPTY_TEMPLATEPARAMETER_ARRAY = new ICPPASTTemplateParameter[0];
/**
* Returns whether this template parameter is a parameter pack.
* @since 5.2
*/
public boolean isParameterPack();
/** /**
* @since 5.1 * @since 5.1
*/ */

View file

@ -7,6 +7,7 @@
* *
* Contributors: * Contributors:
* John Camelon (IBM) - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
@ -16,79 +17,72 @@ import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNameOwner; import org.eclipse.cdt.core.dom.ast.IASTNameOwner;
/** /**
* This is a templated template parameter. * This is a template template parameter as <code> V </code> in
* <code>template&lttemplate&lttypename T&gt class V&gt class CT;</code>
* *
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
*/ */
public interface ICPPASTTemplatedTypeTemplateParameter extends public interface ICPPASTTemplatedTypeTemplateParameter extends ICPPASTTemplateParameter, IASTNameOwner {
ICPPASTTemplateParameter, IASTNameOwner {
/** /**
* PARAMETER * Relation between template template parameter and its (nested) template parameters.
*/ */
public static final ASTNodeProperty PARAMETER = new ASTNodeProperty( public static final ASTNodeProperty PARAMETER = new ASTNodeProperty(
"ICPPASTTemplateTypeTemplateParameter.PARAMETER - Template Parameter"); //$NON-NLS-1$ "ICPPASTTemplateTypeTemplateParameter.PARAMETER [ICPPASTTemplateParameter]"); //$NON-NLS-1$
/** /**
* Get all template parameters. * Relation between template template parameter and its name.
* */
* @return <code>ICPPASTTemplateParameter []</code> public static final ASTNodeProperty PARAMETER_NAME = new ASTNodeProperty(
"ICPPASTTemplateTypeTemplateParameter.PARAMETER_NAME [ICPPASTName]"); //$NON-NLS-1$
/**
* Relation between template template parameter and its default value.
*/
public static final ASTNodeProperty DEFAULT_VALUE = new ASTNodeProperty(
"ICPPASTTemplateTypeTemplateParameter.DEFAULT_VALUE [IASTExpression]"); //$NON-NLS-1$
/**
* Get the nested template parameters.
*/ */
public ICPPASTTemplateParameter[] getTemplateParameters(); public ICPPASTTemplateParameter[] getTemplateParameters();
/** /**
* Add a parameter. * Get the (optional) name of this template template parameter. In case there is no name an
* * empty name is returned.
* @param parm
* <code>ICPPASTTemplateParameter</code>
*/
public void addTemplateParamter(ICPPASTTemplateParameter parm);
/**
* This parameter's name.
*/
public static final ASTNodeProperty PARAMETER_NAME = new ASTNodeProperty(
"ICPPASTTemplateTypeTemplateParameter.PARAMETER_NAME - Template Parameter's Name"); //$NON-NLS-1$
/**
* Get name.
*
* @return <code>IASTName</code>
*/ */
public IASTName getName(); public IASTName getName();
/** /**
* Set name. * Get default value for template template parameter or <code>null</code>.
*
* @param name
* <code>IASTName</code>
*/
public void setName(IASTName name);
/**
* DEFAULT_VALUE is an expession.
*/
public static final ASTNodeProperty DEFAULT_VALUE = new ASTNodeProperty(
"ICPPASTTemplateTypeTemplateParameter.DEFAULT_VALUE - Default Value is an expression"); //$NON-NLS-1$
/**
* Get default value for template type.
*
* @return <code>IASTExpression</code>
*/ */
public IASTExpression getDefaultValue(); public IASTExpression getDefaultValue();
/**
* Set default value for template type.
*
* @param expression
* <code>IASTExpression</code>
*/
public void setDefaultValue(IASTExpression expression);
/** /**
* @since 5.1 * @since 5.1
*/ */
public ICPPASTTemplatedTypeTemplateParameter copy(); public ICPPASTTemplatedTypeTemplateParameter copy();
/**
* Add a nested template parameter.
*/
public void addTemplateParamter(ICPPASTTemplateParameter parm);
/**
* Set whether this template template parameter is a parameter pack.
* @since 5.2
*/
public void setIsParameterPack(boolean val);
/**
* Set the name of this template template parameter.
*/
public void setName(IASTName name);
/**
* Set default value for the template template parameter.
*/
public void setDefaultValue(IASTExpression expression);
} }

View file

@ -0,0 +1,23 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IASTTypeId;
/**
* Type ids in C++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPASTTypeId extends IASTTypeId, ICPPASTPackExpandable {
}

View file

@ -57,4 +57,14 @@ public interface ICPPFunction extends IFunction, ICPPBinding {
* @since 5.2 * @since 5.2
*/ */
public ICPPParameter[] getParameters() throws DOMException; public ICPPParameter[] getParameters() throws DOMException;
/**
* @since 5.2
*/
public int getRequiredArgumentCount() throws DOMException;
/**
* @since 5.2
*/
public boolean hasParameterPack();
} }

View file

@ -21,15 +21,6 @@ import org.eclipse.cdt.core.dom.ast.IPointerType;
*/ */
public interface ICPPFunctionType extends IFunctionType { public interface ICPPFunctionType extends IFunctionType {
/**
* Returns type of implicit <code>this</code>. parameter, or null, if the function
* is not a class method or a static method.
* @deprecated function types don't relate to this pointers at all.
* @noreference This method is not intended to be referenced by clients.
*/
@Deprecated
public IPointerType getThisType();
/** /**
* Returns <code>true</code> for a constant method * Returns <code>true</code> for a constant method
*/ */
@ -39,4 +30,18 @@ public interface ICPPFunctionType extends IFunctionType {
* Returns <code>true</code> for a volatile method * Returns <code>true</code> for a volatile method
*/ */
public boolean isVolatile(); public boolean isVolatile();
/**
* Whether the function type takes variable number of arguments.
* @since 5.2
*/
public boolean takesVarArgs();
/**
* @deprecated function types don't relate to this pointers at all.
* @noreference This method is not intended to be referenced by clients and should be removed.
*/
@Deprecated
public IPointerType getThisType();
} }

View file

@ -6,7 +6,7 @@
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM Corporation - initial API and implementation * Mike Kucera (IBM Corporation) - initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp; package org.eclipse.cdt.core.dom.ast.cpp;
@ -32,7 +32,6 @@ import org.eclipse.cdt.core.parser.IScanner;
/** /**
* Factory for AST nodes for the C++ programming language. * Factory for AST nodes for the C++ programming language.
* *
* @author Mike Kucera
* @since 5.1 * @since 5.1
* @noextend This interface is not intended to be extended by clients. * @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients. * @noimplement This interface is not intended to be implemented by clients.
@ -60,8 +59,23 @@ public interface ICPPNodeFactory extends INodeFactory {
public ICPPASTFunctionDefinition newFunctionDefinition(IASTDeclSpecifier declSpecifier, public ICPPASTFunctionDefinition newFunctionDefinition(IASTDeclSpecifier declSpecifier,
IASTFunctionDeclarator declarator, IASTStatement bodyStatement); IASTFunctionDeclarator declarator, IASTStatement bodyStatement);
/**
* @since 5.2
*/
public ICPPASTDeclarator newDeclarator(IASTName name);
public ICPPASTFunctionDeclarator newFunctionDeclarator(IASTName name); public ICPPASTFunctionDeclarator newFunctionDeclarator(IASTName name);
/**
* @since 5.2
*/
public ICPPASTArrayDeclarator newArrayDeclarator(IASTName name);
/**
* @since 5.2
*/
public ICPPASTFieldDeclarator newFieldDeclarator(IASTName name, IASTExpression bitFieldSize);
public ICPPASTElaboratedTypeSpecifier newElaboratedTypeSpecifier(int kind, IASTName name); public ICPPASTElaboratedTypeSpecifier newElaboratedTypeSpecifier(int kind, IASTName name);
public ICPPASTParameterDeclaration newParameterDeclaration(IASTDeclSpecifier declSpec, IASTDeclarator declarator); public ICPPASTParameterDeclaration newParameterDeclaration(IASTDeclSpecifier declSpec, IASTDeclarator declarator);
@ -106,6 +120,11 @@ public interface ICPPNodeFactory extends INodeFactory {
public ICPPASTWhileStatement newWhileStatement(); public ICPPASTWhileStatement newWhileStatement();
/**
* @since 5.2
*/
public ICPPASTTypeId newTypeId(IASTDeclSpecifier declSpecifier, IASTDeclarator declarator);
public ICPPASTDeleteExpression newDeleteExpression(IASTExpression operand); public ICPPASTDeleteExpression newDeleteExpression(IASTExpression operand);
public IGPPASTSimpleDeclSpecifier newSimpleDeclSpecifierGPP(); public IGPPASTSimpleDeclSpecifier newSimpleDeclSpecifierGPP();
@ -156,6 +175,16 @@ public interface ICPPNodeFactory extends INodeFactory {
public IGPPASTPointerToMember newPointerToMemberGPP(IASTName name); public IGPPASTPointerToMember newPointerToMemberGPP(IASTName name);
/**
* @since 5.2
*/
public ICPPASTInitializerExpression newInitializerExpression(IASTExpression expression);
/**
* @since 5.2
*/
public ICPPASTInitializerList newInitializerList();
public ICPPASTConstructorInitializer newConstructorInitializer(IASTExpression exp); public ICPPASTConstructorInitializer newConstructorInitializer(IASTExpression exp);
public ICPPASTConstructorChainInitializer newConstructorChainInitializer(IASTName memberInitializerId, IASTExpression initializerValue); public ICPPASTConstructorChainInitializer newConstructorChainInitializer(IASTName memberInitializerId, IASTExpression initializerValue);
@ -181,6 +210,11 @@ public interface ICPPNodeFactory extends INodeFactory {
*/ */
public ICPPASTStaticAssertDeclaration newStaticAssertion(IASTExpression condition, ICPPASTLiteralExpression message); public ICPPASTStaticAssertDeclaration newStaticAssertion(IASTExpression condition, ICPPASTLiteralExpression message);
/**
* Creates a new pack expansion expression for the given pattern.
* @since 5.2
*/
public ICPPASTPackExpansionExpression newPackExpansionExpression(IASTExpression pattern);
/** /**
* @deprecated Replaced by {@link #newReferenceOperator(boolean)}. * @deprecated Replaced by {@link #newReferenceOperator(boolean)}.

View file

@ -28,4 +28,10 @@ public interface ICPPParameter extends IParameter, ICPPVariable {
* if there is a default value or not. * if there is a default value or not.
*/ */
public boolean hasDefaultValue(); public boolean hasDefaultValue();
/**
* Returns whether this parameter is a parameter pack.
* @since 5.2
*/
public boolean isParameterPack();
} }

View file

@ -0,0 +1,29 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn (Wind River Systems) - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.IType;
/**
* A parameter pack is not actually a type, however we model it as such in order
* to be able to represent function-types that contain parameter packs.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
* @since 5.2
*/
public interface ICPPParameterPackType extends IType {
/**
* Returns the pattern for the pack-expansion
*/
public IType getType();
}

View file

@ -62,4 +62,10 @@ public interface ICPPTemplateParameter extends ICPPBinding {
* @since 5.1 * @since 5.1
*/ */
ICPPTemplateArgument getDefaultValue(); ICPPTemplateArgument getDefaultValue();
/**
* Returns whether this template parameter is a parameter pack.
* @since 5.2
*/
boolean isParameterPack();
} }

View file

@ -67,6 +67,7 @@ import org.eclipse.cdt.core.dom.ast.IASTWhileStatement;
import org.eclipse.cdt.core.dom.ast.INodeFactory; import org.eclipse.cdt.core.dom.ast.INodeFactory;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator; import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPackExpansionExpression;
import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTCompoundStatementExpression; import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTCompoundStatementExpression;
import org.eclipse.cdt.core.dom.parser.IBuiltinBindingsProvider; import org.eclipse.cdt.core.dom.parser.IBuiltinBindingsProvider;
import org.eclipse.cdt.core.dom.parser.ISourceCodeParser; import org.eclipse.cdt.core.dom.parser.ISourceCodeParser;
@ -515,6 +516,12 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
return n; return n;
} }
protected final <T extends IASTNode> T setRange(T n, IASTNode from, int endOffset) {
final int offset = ((ASTNode) from).getOffset();
((ASTNode) n).setOffsetAndLength(offset, endOffset-offset);
return n;
}
protected final <T extends IASTNode> T setRange(T n, int offset, int endOffset) { protected final <T extends IASTNode> T setRange(T n, int offset, int endOffset) {
((ASTNode) n).setOffsetAndLength(offset, endOffset-offset); ((ASTNode) n).setOffsetAndLength(offset, endOffset-offset);
return n; return n;
@ -525,9 +532,10 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
adjustEndOffset(n, endOffset); adjustEndOffset(n, endOffset);
} }
protected final void adjustEndOffset(IASTNode n, final int endOffset) { protected final <T extends IASTNode> T adjustEndOffset(T n, final int endOffset) {
final ASTNode node = (ASTNode) n; final ASTNode node = (ASTNode) n;
node.setLength(endOffset-node.getOffset()); node.setLength(endOffset-node.getOffset());
return n;
} }
protected final int getEndOffset() { protected final int getEndOffset() {
@ -914,8 +922,8 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
IASTExpression fExpression; IASTExpression fExpression;
final CastAmbiguityMarker fAmbiguityMarker; final CastAmbiguityMarker fAmbiguityMarker;
public BinaryOperator(BinaryOperator left, IASTExpression expression, int operatorToken, int leftPrecedence, int rightPrecedence) { public BinaryOperator(BinaryOperator nextOp, IASTExpression expression, int operatorToken, int leftPrecedence, int rightPrecedence) {
fNext= left; fNext= nextOp;
fOperatorToken= operatorToken; fOperatorToken= operatorToken;
fLeftPrecedence= leftPrecedence; fLeftPrecedence= leftPrecedence;
fRightPrecedence= rightPrecedence; fRightPrecedence= rightPrecedence;
@ -978,6 +986,17 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
} }
return conditionalEx; return conditionalEx;
case IToken.tELLIPSIS:
if (right instanceof ICPPASTPackExpansionExpression) {
((ICPPASTPackExpansionExpression) right).setPattern(left);
int endOffset= ((ASTNode) right).getLength();
setRange(right, left);
adjustEndOffset(right, endOffset);
return right;
}
assert false;
return left;
case IToken.tCOMMA: case IToken.tCOMMA:
IASTExpressionList list; IASTExpressionList list;
if (left instanceof IASTExpressionList) { if (left instanceof IASTExpressionList) {

View file

@ -24,6 +24,7 @@ public class DeclarationOptions {
final public static int NO_FUNCTIONS= 0x40; final public static int NO_FUNCTIONS= 0x40;
final public static int NO_ARRAYS= 0x80; final public static int NO_ARRAYS= 0x80;
final public static int NO_NESTED= 0x100; final public static int NO_NESTED= 0x100;
final public static int ALLOW_PARAMETER_PACKS= 0x200;
public static final DeclarationOptions public static final DeclarationOptions
GLOBAL= new DeclarationOptions(ALLOW_EMPTY_SPECIFIER | ALLOW_CONSTRUCTOR_INITIALIZER), GLOBAL= new DeclarationOptions(ALLOW_EMPTY_SPECIFIER | ALLOW_CONSTRUCTOR_INITIALIZER),
@ -31,7 +32,7 @@ public class DeclarationOptions {
C_MEMBER= new DeclarationOptions(ALLOW_BITFIELD | ALLOW_ABSTRACT), C_MEMBER= new DeclarationOptions(ALLOW_BITFIELD | ALLOW_ABSTRACT),
CPP_MEMBER= new DeclarationOptions(ALLOW_EMPTY_SPECIFIER | ALLOW_BITFIELD), CPP_MEMBER= new DeclarationOptions(ALLOW_EMPTY_SPECIFIER | ALLOW_BITFIELD),
LOCAL= new DeclarationOptions(ALLOW_CONSTRUCTOR_INITIALIZER), LOCAL= new DeclarationOptions(ALLOW_CONSTRUCTOR_INITIALIZER),
PARAMETER= new DeclarationOptions(ALLOW_ABSTRACT), PARAMETER= new DeclarationOptions(ALLOW_ABSTRACT | ALLOW_PARAMETER_PACKS),
TYPEID= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER), TYPEID= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER),
TYPEID_NEW= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER | NO_FUNCTIONS | NO_NESTED), TYPEID_NEW= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER | NO_FUNCTIONS | NO_NESTED),
TYPEID_CONVERSION= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER | NO_FUNCTIONS | NO_NESTED), TYPEID_CONVERSION= new DeclarationOptions(REQUIRE_ABSTRACT | NO_INITIALIZER | NO_FUNCTIONS | NO_NESTED),
@ -47,6 +48,7 @@ public class DeclarationOptions {
final public boolean fAllowConstructorInitializer; final public boolean fAllowConstructorInitializer;
final public boolean fAllowFunctions; final public boolean fAllowFunctions;
final public boolean fAllowNested; final public boolean fAllowNested;
final public boolean fAllowParameterPacks;
public DeclarationOptions(int options) { public DeclarationOptions(int options) {
fAllowEmptySpecifier= (options & ALLOW_EMPTY_SPECIFIER) != 0; fAllowEmptySpecifier= (options & ALLOW_EMPTY_SPECIFIER) != 0;
@ -57,5 +59,6 @@ public class DeclarationOptions {
fAllowConstructorInitializer= fAllowInitializer && (options & ALLOW_CONSTRUCTOR_INITIALIZER) != 0; fAllowConstructorInitializer= fAllowInitializer && (options & ALLOW_CONSTRUCTOR_INITIALIZER) != 0;
fAllowFunctions= (options & NO_FUNCTIONS) == 0; fAllowFunctions= (options & NO_FUNCTIONS) == 0;
fAllowNested= (options & NO_NESTED) == 0; fAllowNested= (options & NO_NESTED) == 0;
fAllowParameterPacks= (options & ALLOW_PARAMETER_PACKS) != 0;
} }
} }

View file

@ -25,6 +25,7 @@ public interface ITypeMarshalBuffer {
final static byte FUNCTION_TYPE= 5; final static byte FUNCTION_TYPE= 5;
final static byte REFERENCE= 6; final static byte REFERENCE= 6;
final static byte POINTER_TO_MEMBER= 7; final static byte POINTER_TO_MEMBER= 7;
final static byte PACK_EXPANSION= 8;
static final byte KIND_MASK = 0xf; static final byte KIND_MASK = 0xf;
final static int FLAG1 = 0x10; final static int FLAG1 = 0x10;

View file

@ -448,7 +448,8 @@ public class Value implements IValue {
private static Object evaluateUnaryExpression(IASTUnaryExpression ue, Map<String, Integer> unknownSigs, List<ICPPUnknownBinding> unknowns, int maxdepth) throws UnknownValueException { private static Object evaluateUnaryExpression(IASTUnaryExpression ue, Map<String, Integer> unknownSigs, List<ICPPUnknownBinding> unknowns, int maxdepth) throws UnknownValueException {
final int unaryOp= ue.getOperator(); final int unaryOp= ue.getOperator();
if (unaryOp == IASTUnaryExpression.op_amper || unaryOp == IASTUnaryExpression.op_star) if (unaryOp == IASTUnaryExpression.op_amper || unaryOp == IASTUnaryExpression.op_star ||
unaryOp == IASTUnaryExpression.op_sizeof || unaryOp == IASTUnaryExpression.op_sizeofParameterPack)
throw UNKNOWN_EX; throw UNKNOWN_EX;
final Object value= evaluate(ue.getOperand(), unknownSigs, unknowns, maxdepth); final Object value= evaluate(ue.getOperand(), unknownSigs, unknowns, maxdepth);

View file

@ -259,6 +259,7 @@ public abstract class VariableReadWriteFlags {
return PDOMName.READ_ACCESS; return PDOMName.READ_ACCESS;
case IASTUnaryExpression.op_sizeof: case IASTUnaryExpression.op_sizeof:
case IASTUnaryExpression.op_sizeofParameterPack:
case IGNUASTUnaryExpression.op_alignOf: case IGNUASTUnaryExpression.op_alignOf:
case IGNUASTUnaryExpression.op_typeof: case IGNUASTUnaryExpression.op_typeof:
return 0; return 0;

View file

@ -17,6 +17,7 @@ import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator; import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
import org.eclipse.cdt.core.dom.ast.IScope; import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode; import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousDeclarator; import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousDeclarator;
@ -28,7 +29,7 @@ import org.eclipse.core.runtime.Assert;
* <br> * <br>
* Example: void f(int (D)); // is D a type? * Example: void f(int (D)); // is D a type?
*/ */
public class CPPASTAmbiguousDeclarator extends ASTAmbiguousNode implements IASTAmbiguousDeclarator { public class CPPASTAmbiguousDeclarator extends ASTAmbiguousNode implements IASTAmbiguousDeclarator, ICPPASTDeclarator {
private IASTDeclarator[] dtors = new IASTDeclarator[2]; private IASTDeclarator[] dtors = new IASTDeclarator[2];
private int dtorPos=-1; private int dtorPos=-1;
@ -124,4 +125,13 @@ public class CPPASTAmbiguousDeclarator extends ASTAmbiguousNode implements IASTA
assertNotFrozen(); assertNotFrozen();
Assert.isLegal(false); Assert.isLegal(false);
} }
public boolean declaresParameterPack() {
return false;
}
public void setDeclaresParameterPack(boolean val) {
assertNotFrozen();
Assert.isLegal(false);
}
} }

View file

@ -0,0 +1,115 @@
/*******************************************************************************
* Copyright (c) 2008, 2009 IBM Wind River Systems, Inc. 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:
* Markus Schorn - Initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode;
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.IASTAmbiguousParameterDeclaration;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
import org.eclipse.core.runtime.Assert;
/**
* Handles ambiguities for ellipsis in parameter declaration.
* <br>
* template<typename... T> void function(T ...); // is T a parameter pack?
*/
public class CPPASTAmbiguousParameterDeclaration extends ASTAmbiguousNode implements
IASTAmbiguousParameterDeclaration, ICPPASTParameterDeclaration {
private ICPPASTParameterDeclaration fParameterDecl;
public CPPASTAmbiguousParameterDeclaration(ICPPASTParameterDeclaration decl) {
fParameterDecl= decl;
}
public void addParameterDeclaration(IASTParameterDeclaration d) {
assert false;
}
@Override
public IASTNode resolveAmbiguity(ASTVisitor resolver) {
final IASTAmbiguityParent owner= (IASTAmbiguityParent) getParent();
// Setup the ast to use the alternative
owner.replace(this, fParameterDecl);
IType t= CPPVisitor.createParameterType(fParameterDecl, true);
if (!(t instanceof ICPPParameterPackType) ||
!SemanticUtil.containsParameterPack(((ICPPParameterPackType) t).getType())) {
final ICPPASTDeclarator dtor = fParameterDecl.getDeclarator();
dtor.setDeclaresParameterPack(false);
adjustOffsets(dtor);
((ICPPASTFunctionDeclarator) fParameterDecl.getParent()).setVarArgs(true);
}
return fParameterDecl;
}
private void adjustOffsets(final ICPPASTDeclarator dtor) {
IASTPointerOperator[] ptrOps= dtor.getPointerOperators();
final ASTNode asNode = (ASTNode) dtor;
if (ptrOps.length > 0) {
final ASTNode first = (ASTNode)ptrOps[0];
final ASTNode last = (ASTNode)ptrOps[ptrOps.length-1];
asNode.setOffsetAndLength(first.getOffset(), last.getOffset() + last.getLength());
} else {
asNode.setOffsetAndLength(0, 0);
}
}
public IASTParameterDeclaration[] getParameterDeclarations() {
return new IASTParameterDeclaration[] {fParameterDecl};
}
@Override
public IASTNode[] getNodes() {
return getParameterDeclarations();
}
public IASTDeclSpecifier getDeclSpecifier() {
return fParameterDecl.getDeclSpecifier();
}
public ICPPASTDeclarator getDeclarator() {
return fParameterDecl.getDeclarator();
}
public void setDeclSpecifier(IASTDeclSpecifier declSpec) {
Assert.isLegal(false);
}
public void setDeclarator(IASTDeclarator declarator) {
Assert.isLegal(false);
}
public ICPPASTParameterDeclaration copy() {
Assert.isLegal(false);
return null;
}
public boolean isParameterPack() {
Assert.isLegal(false);
return true;
}
}

View file

@ -12,17 +12,18 @@
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import com.ibm.icu.text.MessageFormat;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTIdExpression; import org.eclipse.cdt.core.dom.ast.IASTIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTAmbiguousTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTAmbiguousTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPackExpansionExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode; import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode;
import org.eclipse.cdt.internal.core.parser.ParserMessages; import org.eclipse.core.runtime.Assert;
/** /**
* Ambiguity node for deciding between type-id and id-expression in a template argument. * Ambiguity node for deciding between type-id and id-expression in a template argument.
@ -32,21 +33,22 @@ public class CPPASTAmbiguousTemplateArgument extends ASTAmbiguousNode implements
private List<IASTNode> fNodes; private List<IASTNode> fNodes;
/** /**
* @param nodes nodes of type {@link IASTTypeId} or {@link IASTIdExpression} * @param nodes nodes of type {@link IASTTypeId}, {@link IASTIdExpression} or {@link ICPPASTPackExpansionExpression}.
*/
/*
* We can replace this with a version taking ICPPASTTemplateArgument...
* in the future
*/ */
public CPPASTAmbiguousTemplateArgument(IASTNode... nodes) { public CPPASTAmbiguousTemplateArgument(IASTNode... nodes) {
fNodes= new ArrayList<IASTNode>(2); fNodes= new ArrayList<IASTNode>(2);
for(IASTNode node : nodes) { for(IASTNode node : nodes) {
if(node instanceof IASTTypeId || node instanceof IASTIdExpression) { if (node instanceof IASTTypeId || node instanceof IASTIdExpression) {
fNodes.add(node);
} else if (node instanceof ICPPASTPackExpansionExpression) {
final IASTExpression pattern = ((ICPPASTPackExpansionExpression) node).getPattern();
if (pattern instanceof IASTIdExpression) {
fNodes.add(node); fNodes.add(node);
} else { } else {
String ns= node == null ? "null" : node.getClass().getName(); //$NON-NLS-1$ Assert.isLegal(false, pattern == null ? "null" : pattern.getClass().getName()); //$NON-NLS-1$
String msg= MessageFormat.format(ParserMessages.getString("CPPASTAmbiguousTemplateArgument_InvalidConstruction"), new Object[] {ns}); //$NON-NLS-1$ }
throw new IllegalArgumentException(msg); } else {
Assert.isLegal(false, node == null ? "null" : node.getClass().getName()); //$NON-NLS-1$
} }
} }
} }
@ -70,6 +72,11 @@ public class CPPASTAmbiguousTemplateArgument extends ASTAmbiguousNode implements
addNode(idExpression); addNode(idExpression);
} }
public void addIdExpression(IASTExpression idExpression) {
assertNotFrozen();
addNode(idExpression);
}
private void addNode(IASTNode node) { private void addNode(IASTNode node) {
fNodes.add(node); fNodes.add(node);
node.setParent(this); node.setParent(this);

View file

@ -1,27 +1,27 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTArrayDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTArrayModifier; import org.eclipse.cdt.core.dom.ast.IASTArrayModifier;
import org.eclipse.cdt.core.dom.ast.IASTInitializer; import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTArrayDeclarator;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
/** /**
* @author jcamelon * Array declarator for c++.
*/ */
public class CPPASTArrayDeclarator extends CPPASTDeclarator implements IASTArrayDeclarator { public class CPPASTArrayDeclarator extends CPPASTDeclarator implements ICPPASTArrayDeclarator {
private IASTArrayModifier [] arrayMods = null; private IASTArrayModifier [] arrayMods = null;
private int arrayModsPos=-1; private int arrayModsPos=-1;

View file

@ -1,12 +1,12 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Bryan Wilkinson (QNX) * Bryan Wilkinson (QNX)
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
@ -27,14 +27,14 @@ import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPSemantics; import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPSemantics;
/** /**
* @author jcamelon * Base class specifier
*/ */
public class CPPASTBaseSpecifier extends ASTNode implements public class CPPASTBaseSpecifier extends ASTNode implements ICPPASTBaseSpecifier, IASTCompletionContext {
ICPPASTBaseSpecifier, IASTCompletionContext {
private boolean isVirtual; private boolean isVirtual;
private int visibility; private int visibility;
private IASTName name; private IASTName name;
private boolean fIsPackExpansion;
public CPPASTBaseSpecifier() { public CPPASTBaseSpecifier() {
@ -54,6 +54,7 @@ public class CPPASTBaseSpecifier extends ASTNode implements
CPPASTBaseSpecifier copy = new CPPASTBaseSpecifier(name == null ? null : name.copy()); CPPASTBaseSpecifier copy = new CPPASTBaseSpecifier(name == null ? null : name.copy());
copy.isVirtual = isVirtual; copy.isVirtual = isVirtual;
copy.visibility = visibility; copy.visibility = visibility;
copy.fIsPackExpansion= fIsPackExpansion;
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
return copy; return copy;
} }
@ -129,9 +130,9 @@ public class CPPASTBaseSpecifier extends ASTNode implements
} }
} }
for (int i = 0; i < bindings.length; i++) { for (IBinding binding : bindings) {
if (bindings[i] instanceof ICPPClassType) { if (binding instanceof ICPPClassType) {
ICPPClassType base = (ICPPClassType) bindings[i]; ICPPClassType base = (ICPPClassType) binding;
try { try {
int key = base.getKey(); int key = base.getKey();
if (key == ICPPClassType.k_class && if (key == ICPPClassType.k_class &&
@ -145,4 +146,13 @@ public class CPPASTBaseSpecifier extends ASTNode implements
return filtered.toArray(new IBinding[filtered.size()]); return filtered.toArray(new IBinding[filtered.size()]);
} }
public boolean isPackExpansion() {
return fIsPackExpansion;
}
public void setIsPackExpansion(boolean val) {
assertNotFrozen();
fIsPackExpansion= val;
}
} }

View file

@ -43,6 +43,7 @@ public class CPPASTConstructorChainInitializer extends ASTNode implements
private IASTName name; private IASTName name;
private IASTExpression value; private IASTExpression value;
private boolean fIsPackExpansion;
public CPPASTConstructorChainInitializer() { public CPPASTConstructorChainInitializer() {
@ -58,6 +59,7 @@ public class CPPASTConstructorChainInitializer extends ASTNode implements
copy.setMemberInitializerId(name == null ? null : name.copy()); copy.setMemberInitializerId(name == null ? null : name.copy());
copy.setInitializerValue(value == null ? null : value.copy()); copy.setInitializerValue(value == null ? null : value.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
copy.fIsPackExpansion= fIsPackExpansion;
return copy; return copy;
} }
@ -173,4 +175,13 @@ public class CPPASTConstructorChainInitializer extends ASTNode implements
return null; return null;
} }
public boolean isPackExpansion() {
return fIsPackExpansion;
}
public void setIsPackExpansion(boolean val) {
assertNotFrozen();
fIsPackExpansion= val;
}
} }

View file

@ -1,12 +1,13 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -18,12 +19,13 @@ 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.IASTAmbiguityParent;
/** /**
* @author jcamelon * Initializer in parenthesis.
*/ */
public class CPPASTConstructorInitializer extends ASTNode implements public class CPPASTConstructorInitializer extends ASTNode implements
ICPPASTConstructorInitializer, IASTAmbiguityParent { ICPPASTConstructorInitializer, IASTAmbiguityParent {
private IASTExpression exp; private IASTExpression exp;
private boolean fIsPackExpansion;
public CPPASTConstructorInitializer() { public CPPASTConstructorInitializer() {
@ -36,6 +38,7 @@ public class CPPASTConstructorInitializer extends ASTNode implements
public CPPASTConstructorInitializer copy() { public CPPASTConstructorInitializer copy() {
CPPASTConstructorInitializer copy = new CPPASTConstructorInitializer(exp == null ? null : exp.copy()); CPPASTConstructorInitializer copy = new CPPASTConstructorInitializer(exp == null ? null : exp.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
copy.fIsPackExpansion= fIsPackExpansion;
return copy; return copy;
} }
@ -79,4 +82,13 @@ public class CPPASTConstructorInitializer extends ASTNode implements
exp = (IASTExpression) other; exp = (IASTExpression) other;
} }
} }
public boolean isPackExpansion() {
return fIsPackExpansion;
}
public void setIsPackExpansion(boolean val) {
assertNotFrozen();
fIsPackExpansion= val;
}
} }

View file

@ -24,6 +24,7 @@ import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator; import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration; import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassScope; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassScope;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
@ -34,12 +35,12 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
/** /**
* C++ specific declarator. * C++ specific declarator.
*/ */
public class CPPASTDeclarator extends ASTNode implements IASTDeclarator { public class CPPASTDeclarator extends ASTNode implements ICPPASTDeclarator {
private IASTInitializer initializer; private IASTInitializer initializer;
private IASTName name; private IASTName name;
private IASTDeclarator nested; private IASTDeclarator nested;
private IASTPointerOperator[] pointerOps = null; private IASTPointerOperator[] pointerOps = null;
private int pointerOpsPos= -1; private boolean isPackExpansion;
public CPPASTDeclarator() { public CPPASTDeclarator() {
} }
@ -64,14 +65,19 @@ public class CPPASTDeclarator extends ASTNode implements IASTDeclarator {
copy.setName(name == null ? null : name.copy()); copy.setName(name == null ? null : name.copy());
copy.setInitializer(initializer == null ? null : initializer.copy()); copy.setInitializer(initializer == null ? null : initializer.copy());
copy.setNestedDeclarator(nested == null ? null : nested.copy()); copy.setNestedDeclarator(nested == null ? null : nested.copy());
copy.isPackExpansion= isPackExpansion;
for(IASTPointerOperator pointer : getPointerOperators()) for(IASTPointerOperator pointer : getPointerOperators())
copy.addPointerOperator(pointer == null ? null : pointer.copy()); copy.addPointerOperator(pointer == null ? null : pointer.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
} }
public boolean declaresParameterPack() {
return isPackExpansion;
}
public IASTPointerOperator[] getPointerOperators() { public IASTPointerOperator[] getPointerOperators() {
if (pointerOps == null) return IASTPointerOperator.EMPTY_ARRAY; if (pointerOps == null) return IASTPointerOperator.EMPTY_ARRAY;
pointerOps = (IASTPointerOperator[]) ArrayUtil.removeNullsAfter(IASTPointerOperator.class, pointerOps, pointerOpsPos); pointerOps = (IASTPointerOperator[]) ArrayUtil.trim(IASTPointerOperator.class, pointerOps);
return pointerOps; return pointerOps;
} }
@ -101,7 +107,7 @@ public class CPPASTDeclarator extends ASTNode implements IASTDeclarator {
if (operator != null) { if (operator != null) {
operator.setParent(this); operator.setParent(this);
operator.setPropertyInParent(POINTER_OPERATOR); operator.setPropertyInParent(POINTER_OPERATOR);
pointerOps = (IASTPointerOperator[]) ArrayUtil.append(IASTPointerOperator.class, pointerOps, ++pointerOpsPos, operator); pointerOps = (IASTPointerOperator[]) ArrayUtil.append(IASTPointerOperator.class, pointerOps, operator);
} }
} }
@ -123,6 +129,11 @@ public class CPPASTDeclarator extends ASTNode implements IASTDeclarator {
} }
} }
public void setDeclaresParameterPack(boolean val) {
assertNotFrozen();
isPackExpansion= val;
}
@Override @Override
public boolean accept(ASTVisitor action) { public boolean accept(ASTVisitor action) {
if (action.shouldVisitDeclarators) { if (action.shouldVisitDeclarators) {
@ -133,10 +144,14 @@ public class CPPASTDeclarator extends ASTNode implements IASTDeclarator {
} }
} }
for (int i = 0; i <= pointerOpsPos; i++) { if (pointerOps != null) {
if (!pointerOps[i].accept(action)) for (IASTPointerOperator op : pointerOps) {
if (op == null)
break;
if (!op.accept(action))
return false; return false;
} }
}
if (nested == null && name != null) { if (nested == null && name != null) {
IASTDeclarator outermost= ASTQueries.findOutermostDeclarator(this); IASTDeclarator outermost= ASTQueries.findOutermostDeclarator(this);

View file

@ -1,32 +1,31 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldDeclarator;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent; import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/** /**
* @author jcamelon * Field declarator for c++.
*/ */
public class CPPASTFieldDeclarator extends CPPASTDeclarator implements public class CPPASTFieldDeclarator extends CPPASTDeclarator implements
IASTFieldDeclarator, IASTAmbiguityParent { ICPPASTFieldDeclarator, IASTAmbiguityParent {
private IASTExpression bitField; private IASTExpression bitField;
public CPPASTFieldDeclarator() { public CPPASTFieldDeclarator() {
} }

View file

@ -19,18 +19,19 @@ import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionScope; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionScope;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/** /**
* Represents a function declarator. * Represents a function declarator.
*/ */
public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPASTFunctionDeclarator { public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPASTFunctionDeclarator,
private IASTParameterDeclaration[] parameters = null; IASTAmbiguityParent {
private int parametersPos = -1; private ICPPASTParameterDeclaration[] parameters = null;
private IASTTypeId[] typeIds = NO_EXCEPTION_SPECIFICATION; private IASTTypeId[] typeIds = NO_EXCEPTION_SPECIFICATION;
private int typeIdsPos = -1;
private boolean varArgs; private boolean varArgs;
private boolean pureVirtual; private boolean pureVirtual;
@ -63,11 +64,11 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
return copy; return copy;
} }
public IASTParameterDeclaration[] getParameters() { public ICPPASTParameterDeclaration[] getParameters() {
if (parameters == null) if (parameters == null)
return IASTParameterDeclaration.EMPTY_PARAMETERDECLARATION_ARRAY; return ICPPASTParameterDeclaration.EMPTY_CPPPARAMETERDECLARATION_ARRAY;
return parameters= ArrayUtil.trimAt(IASTParameterDeclaration.class, parameters, parametersPos); return parameters= ArrayUtil.trim(parameters);
} }
public void addParameterDeclaration(IASTParameterDeclaration parameter) { public void addParameterDeclaration(IASTParameterDeclaration parameter) {
@ -75,7 +76,7 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
if (parameter != null) { if (parameter != null) {
parameter.setParent(this); parameter.setParent(this);
parameter.setPropertyInParent(FUNCTION_PARAMETER); parameter.setPropertyInParent(FUNCTION_PARAMETER);
parameters = (IASTParameterDeclaration[]) ArrayUtil.append(IASTParameterDeclaration.class, parameters, ++parametersPos, parameter); parameters = (ICPPASTParameterDeclaration[]) ArrayUtil.append(ICPPASTParameterDeclaration.class, parameters, parameter);
} }
} }
@ -107,7 +108,7 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
} }
public IASTTypeId[] getExceptionSpecification() { public IASTTypeId[] getExceptionSpecification() {
return typeIds= ArrayUtil.trimAt(IASTTypeId.class, typeIds, typeIdsPos); return typeIds= ArrayUtil.trim(typeIds);
} }
public void setEmptyExceptionSpecification() { public void setEmptyExceptionSpecification() {
@ -118,7 +119,8 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
public void addExceptionSpecificationTypeId(IASTTypeId typeId) { public void addExceptionSpecificationTypeId(IASTTypeId typeId) {
assertNotFrozen(); assertNotFrozen();
if (typeId != null) { if (typeId != null) {
typeIds = (IASTTypeId[]) ArrayUtil.append(IASTTypeId.class, typeIds, ++typeIdsPos, typeId); assert typeIds != null;
typeIds = ArrayUtil.append(typeIds, typeId);
typeId.setParent(this); typeId.setParent(this);
typeId.setPropertyInParent(EXCEPTION_TYPEID); typeId.setPropertyInParent(EXCEPTION_TYPEID);
} }
@ -135,7 +137,7 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
@Deprecated @Deprecated
public org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer[] getConstructorChain() { public org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer[] getConstructorChain() {
if (CPPVisitor.findTypeRelevantDeclarator(this) == this) { if (ASTQueries.findTypeRelevantDeclarator(this) == this) {
IASTNode parent= getParent(); IASTNode parent= getParent();
while(!(parent instanceof IASTDeclaration)) { while(!(parent instanceof IASTDeclaration)) {
if (parent == null) if (parent == null)
@ -168,7 +170,7 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
if (node instanceof IASTParameterDeclaration) if (node instanceof IASTParameterDeclaration)
return null; return null;
if (CPPVisitor.findTypeRelevantDeclarator(this) == this) { if (ASTQueries.findTypeRelevantDeclarator(this) == this) {
scope = new CPPFunctionScope(this); scope = new CPPFunctionScope(this);
} }
return scope; return scope;
@ -190,4 +192,18 @@ public class CPPASTFunctionDeclarator extends CPPASTDeclarator implements ICPPAS
return super.postAccept(action); return super.postAccept(action);
} }
public void replace(IASTNode child, IASTNode other) {
if (parameters != null) {
for (int i = 0; i < parameters.length; ++i) {
if (child == parameters[i]) {
other.setPropertyInParent(child.getPropertyInParent());
other.setParent(child.getParent());
parameters[i] = (ICPPASTParameterDeclaration) other;
return;
}
}
}
assert false;
}
} }

View file

@ -1,29 +1,31 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerExpression;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode; 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.IASTAmbiguityParent;
/** /**
* @author jcamelon * Initializer expression.
*/ */
public class CPPASTInitializerExpression extends ASTNode implements public class CPPASTInitializerExpression extends ASTNode implements
IASTInitializerExpression, IASTAmbiguityParent { ICPPASTInitializerExpression, IASTAmbiguityParent {
private IASTExpression exp; private IASTExpression exp;
private boolean fIsPackExpansion;
public CPPASTInitializerExpression() { public CPPASTInitializerExpression() {
@ -36,6 +38,7 @@ public class CPPASTInitializerExpression extends ASTNode implements
public CPPASTInitializerExpression copy() { public CPPASTInitializerExpression copy() {
CPPASTInitializerExpression copy = new CPPASTInitializerExpression(exp == null ? null : exp.copy()); CPPASTInitializerExpression copy = new CPPASTInitializerExpression(exp == null ? null : exp.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
copy.fIsPackExpansion= fIsPackExpansion;
return copy; return copy;
} }
@ -80,5 +83,13 @@ public class CPPASTInitializerExpression extends ASTNode implements
exp = (IASTExpression) other; exp = (IASTExpression) other;
} }
} }
public boolean isPackExpansion() {
return fIsPackExpansion;
}
public void setIsPackExpansion(boolean val) {
assertNotFrozen();
fIsPackExpansion= val;
}
} }

View file

@ -13,17 +13,18 @@ package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTInitializer; import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTInitializerList; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerList;
import org.eclipse.cdt.core.parser.util.ArrayUtil; 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.ASTNode;
/** /**
* e.g.: int a[]= {1,2,3}; * e.g.: int a[]= {1,2,3};
*/ */
public class CPPASTInitializerList extends ASTNode implements IASTInitializerList { public class CPPASTInitializerList extends ASTNode implements ICPPASTInitializerList {
private IASTInitializer [] initializers = null; private IASTInitializer [] initializers = null;
private int initializersPos=-1; private int initializersPos=-1;
private int actualLength; private int actualLength;
private boolean fIsPackExpansion;
public CPPASTInitializerList copy() { public CPPASTInitializerList copy() {
CPPASTInitializerList copy = new CPPASTInitializerList(); CPPASTInitializerList copy = new CPPASTInitializerList();
@ -31,6 +32,7 @@ public class CPPASTInitializerList extends ASTNode implements IASTInitializerLis
copy.addInitializer(initializer == null ? null : initializer.copy()); copy.addInitializer(initializer == null ? null : initializer.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
copy.actualLength= getSize(); copy.actualLength= getSize();
copy.fIsPackExpansion= fIsPackExpansion;
return copy; return copy;
} }
@ -81,4 +83,13 @@ public class CPPASTInitializerList extends ASTNode implements IASTInitializerLis
return true; return true;
} }
public boolean isPackExpansion() {
return fIsPackExpansion;
}
public void setIsPackExpansion(boolean val) {
assertNotFrozen();
fIsPackExpansion= val;
}
} }

View file

@ -0,0 +1,86 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPackExpansionExpression;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/**
* Implementation of pack expansion expression.
*/
public class CPPASTPackExpansionExpression extends ASTNode implements ICPPASTPackExpansionExpression, IASTAmbiguityParent {
private IASTExpression fPattern;
public CPPASTPackExpansionExpression(IASTExpression pattern) {
setPattern(pattern);
}
public void setPattern(IASTExpression pattern) {
assertNotFrozen();
fPattern= pattern;
if (pattern != null) {
pattern.setParent(this);
pattern.setPropertyInParent(ICPPASTPackExpansionExpression.PATTERN);
}
}
public IASTExpression getPattern() {
return fPattern;
}
public IASTExpression copy() {
CPPASTPackExpansionExpression copy = new CPPASTPackExpansionExpression(fPattern.copy());
copy.setOffsetAndLength(this);
return copy;
}
public IType getExpressionType() {
return new CPPParameterPackType(fPattern.getExpressionType());
}
public boolean isLValue() {
return fPattern.isLValue();
}
@Override
public boolean accept(ASTVisitor visitor) {
if (visitor.shouldVisitExpressions) {
switch (visitor.visit(this)) {
case ASTVisitor.PROCESS_ABORT: return false;
case ASTVisitor.PROCESS_SKIP: return true;
default : break;
}
}
if (!fPattern.accept(visitor)) {
return false;
}
if (visitor.shouldVisitExpressions && visitor.leave(this) == ASTVisitor.PROCESS_ABORT) {
return false;
}
return true;
}
public void replace(IASTNode child, IASTNode other) {
if (child == fPattern) {
other.setPropertyInParent(child.getPropertyInParent());
other.setParent(child.getParent());
fPattern = (IASTExpression) other;
}
}
}

View file

@ -1,12 +1,12 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -15,18 +15,19 @@ import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier; import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator; import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode; 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.IASTAmbiguityParent;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
/** /**
* @author jcamelon * Function parameter or non-type template parameter declaration.
*/ */
public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParameterDeclaration, IASTAmbiguityParent { public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParameterDeclaration, IASTAmbiguityParent {
private IASTDeclSpecifier declSpec; private IASTDeclSpecifier fDeclSpec;
private IASTDeclarator declarator; private ICPPASTDeclarator fDeclarator;
public CPPASTParameterDeclaration() { public CPPASTParameterDeclaration() {
} }
@ -36,25 +37,29 @@ public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParame
setDeclarator(declarator); setDeclarator(declarator);
} }
public boolean isParameterPack() {
return fDeclarator != null && CPPVisitor.findInnermostDeclarator(fDeclarator).declaresParameterPack();
}
public CPPASTParameterDeclaration copy() { public CPPASTParameterDeclaration copy() {
CPPASTParameterDeclaration copy = new CPPASTParameterDeclaration(); CPPASTParameterDeclaration copy = new CPPASTParameterDeclaration();
copy.setDeclSpecifier(declSpec == null ? null : declSpec.copy()); copy.setDeclSpecifier(fDeclSpec == null ? null : fDeclSpec.copy());
copy.setDeclarator(declarator == null ? null : declarator.copy()); copy.setDeclarator(fDeclarator == null ? null : fDeclarator.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
return copy; return copy;
} }
public IASTDeclSpecifier getDeclSpecifier() { public IASTDeclSpecifier getDeclSpecifier() {
return declSpec; return fDeclSpec;
} }
public IASTDeclarator getDeclarator() { public ICPPASTDeclarator getDeclarator() {
return declarator; return fDeclarator;
} }
public void setDeclSpecifier(IASTDeclSpecifier declSpec) { public void setDeclSpecifier(IASTDeclSpecifier declSpec) {
assertNotFrozen(); assertNotFrozen();
this.declSpec = declSpec; this.fDeclSpec = declSpec;
if (declSpec != null) { if (declSpec != null) {
declSpec.setParent(this); declSpec.setParent(this);
declSpec.setPropertyInParent(DECL_SPECIFIER); declSpec.setPropertyInParent(DECL_SPECIFIER);
@ -63,10 +68,12 @@ public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParame
public void setDeclarator(IASTDeclarator declarator) { public void setDeclarator(IASTDeclarator declarator) {
assertNotFrozen(); assertNotFrozen();
this.declarator = declarator; if (declarator instanceof ICPPASTDeclarator) {
if (declarator != null) { fDeclarator = (ICPPASTDeclarator) declarator;
declarator.setParent(this); declarator.setParent(this);
declarator.setPropertyInParent(DECLARATOR); declarator.setPropertyInParent(DECLARATOR);
} else {
fDeclarator= null;
} }
} }
@ -80,8 +87,8 @@ public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParame
} }
} }
if( declSpec != null ) if( !declSpec.accept( action ) ) return false; if( fDeclSpec != null ) if( !fDeclSpec.accept( action ) ) return false;
if( declarator != null ) if( !declarator.accept( action ) ) return false; if( fDeclarator != null ) if( !fDeclarator.accept( action ) ) return false;
if( action.shouldVisitParameterDeclarations ){ if( action.shouldVisitParameterDeclarations ){
switch( action.leave( this ) ){ switch( action.leave( this ) ){
@ -94,10 +101,10 @@ public class CPPASTParameterDeclaration extends ASTNode implements ICPPASTParame
} }
public void replace(IASTNode child, IASTNode other) { public void replace(IASTNode child, IASTNode other) {
if (child == declarator) { if (child == fDeclarator) {
other.setPropertyInParent(child.getPropertyInParent()); other.setPropertyInParent(child.getPropertyInParent());
other.setParent(child.getParent()); other.setParent(child.getParent());
declarator= (IASTDeclarator) other; fDeclarator= (ICPPASTDeclarator) other;
} }
} }
} }

View file

@ -1,12 +1,12 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -19,49 +19,60 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTVisitor;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode; import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
/** /**
* @author jcamelon * Template type parameter as in <code>template &lttypename T&gt class X;</code>
*/ */
public class CPPASTSimpleTypeTemplateParameter extends ASTNode implements public class CPPASTSimpleTypeTemplateParameter extends ASTNode implements ICPPASTSimpleTypeTemplateParameter {
ICPPASTSimpleTypeTemplateParameter {
private int type; private IASTName fName;
private IASTName name; private IASTTypeId fTypeId;
private IASTTypeId typeId; private boolean fUsesKeywordClass;
private boolean fIsParameterPack;
public CPPASTSimpleTypeTemplateParameter() { public CPPASTSimpleTypeTemplateParameter() {
} }
public CPPASTSimpleTypeTemplateParameter(int type, IASTName name, IASTTypeId typeId) { public CPPASTSimpleTypeTemplateParameter(int type, IASTName name, IASTTypeId typeId) {
this.type = type; fUsesKeywordClass= type == st_class;
setName(name); setName(name);
setDefaultType(typeId); setDefaultType(typeId);
} }
public CPPASTSimpleTypeTemplateParameter copy() { public CPPASTSimpleTypeTemplateParameter copy() {
CPPASTSimpleTypeTemplateParameter copy = new CPPASTSimpleTypeTemplateParameter(); CPPASTSimpleTypeTemplateParameter copy = new CPPASTSimpleTypeTemplateParameter();
copy.type = type; copy.fUsesKeywordClass = fUsesKeywordClass;
copy.setName(name == null ? null : name.copy()); copy.fIsParameterPack= fIsParameterPack;
copy.setDefaultType(typeId == null ? null : typeId.copy()); copy.setName(fName == null ? null : fName.copy());
copy.setDefaultType(fTypeId == null ? null : fTypeId.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
return copy; return copy;
} }
public boolean isParameterPack() {
return fIsParameterPack;
}
public void setIsParameterPack(boolean val) {
assertNotFrozen();
fIsParameterPack= val;
}
public int getParameterType() { public int getParameterType() {
return type; return fUsesKeywordClass ? st_class : st_typename;
} }
public void setParameterType(int value) { public void setParameterType(int value) {
assertNotFrozen(); assertNotFrozen();
this.type = value; fUsesKeywordClass = value == st_class;
} }
public IASTName getName() { public IASTName getName() {
return name; return fName;
} }
public void setName(IASTName name) { public void setName(IASTName name) {
assertNotFrozen(); assertNotFrozen();
this.name = name; this.fName = name;
if (name != null) { if (name != null) {
name.setParent(this); name.setParent(this);
name.setPropertyInParent(PARAMETER_NAME); name.setPropertyInParent(PARAMETER_NAME);
@ -69,12 +80,12 @@ public class CPPASTSimpleTypeTemplateParameter extends ASTNode implements
} }
public IASTTypeId getDefaultType() { public IASTTypeId getDefaultType() {
return typeId; return fTypeId;
} }
public void setDefaultType(IASTTypeId typeId) { public void setDefaultType(IASTTypeId typeId) {
assertNotFrozen(); assertNotFrozen();
this.typeId = typeId; this.fTypeId = typeId;
if (typeId != null) { if (typeId != null) {
typeId.setParent(this); typeId.setParent(this);
typeId.setPropertyInParent(DEFAULT_TYPE); typeId.setPropertyInParent(DEFAULT_TYPE);
@ -91,8 +102,8 @@ public class CPPASTSimpleTypeTemplateParameter extends ASTNode implements
} }
} }
if (name != null) if (!name.accept(action)) return false; if (fName != null) if (!fName.accept(action)) return false;
if (typeId != null) if (!typeId.accept(action)) return false; if (fTypeId != null) if (!fTypeId.accept(action)) return false;
if (action.shouldVisitTemplateParameters && action instanceof ICPPASTVisitor) { if (action.shouldVisitTemplateParameters && action instanceof ICPPASTVisitor) {
switch (((ICPPASTVisitor) action).leave(this)) { switch (((ICPPASTVisitor) action).leave(this)) {
@ -105,7 +116,7 @@ public class CPPASTSimpleTypeTemplateParameter extends ASTNode implements
} }
public int getRoleForName(IASTName n) { public int getRoleForName(IASTName n) {
if (n == name) if (n == fName)
return r_declaration; return r_declaration;
return r_unclear; return r_unclear;
} }

View file

@ -1,12 +1,12 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -23,11 +23,15 @@ 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.IASTAmbiguityParent;
/** /**
* @author jcamelon * Template template parameter
*/ */
public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
ICPPASTTemplatedTypeTemplateParameter, IASTAmbiguityParent { ICPPASTTemplatedTypeTemplateParameter, IASTAmbiguityParent {
private ICPPASTTemplateParameter [] fNestedParameters = null;
private boolean fIsParameterPack;
private IASTName fName;
private IASTExpression fDefaultValue;
public CPPASTTemplatedTypeTemplateParameter() { public CPPASTTemplatedTypeTemplateParameter() {
} }
@ -39,8 +43,9 @@ public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
public CPPASTTemplatedTypeTemplateParameter copy() { public CPPASTTemplatedTypeTemplateParameter copy() {
CPPASTTemplatedTypeTemplateParameter copy = new CPPASTTemplatedTypeTemplateParameter(); CPPASTTemplatedTypeTemplateParameter copy = new CPPASTTemplatedTypeTemplateParameter();
copy.setName(name == null ? null : name.copy()); copy.setName(fName == null ? null : fName.copy());
copy.setDefaultValue(defaultValue == null ? null : defaultValue.copy()); copy.setDefaultValue(fDefaultValue == null ? null : fDefaultValue.copy());
copy.fIsParameterPack= fIsParameterPack;
for(ICPPASTTemplateParameter param : getTemplateParameters()) for(ICPPASTTemplateParameter param : getTemplateParameters())
copy.addTemplateParamter(param == null ? null : param.copy()); copy.addTemplateParamter(param == null ? null : param.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
@ -48,32 +53,39 @@ public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
} }
public ICPPASTTemplateParameter[] getTemplateParameters() { public ICPPASTTemplateParameter[] getTemplateParameters() {
if( parameters == null ) return ICPPASTTemplateParameter.EMPTY_TEMPLATEPARAMETER_ARRAY; if (fNestedParameters == null)
parameters = (ICPPASTTemplateParameter[]) ArrayUtil.removeNullsAfter( ICPPASTTemplateParameter.class, parameters, parametersPos ); return ICPPASTTemplateParameter.EMPTY_TEMPLATEPARAMETER_ARRAY;
return parameters; fNestedParameters = (ICPPASTTemplateParameter[]) ArrayUtil.trim(ICPPASTTemplateParameter.class, fNestedParameters);
return fNestedParameters;
} }
public void addTemplateParamter(ICPPASTTemplateParameter parm) { public void addTemplateParamter(ICPPASTTemplateParameter parm) {
assertNotFrozen(); assertNotFrozen();
if(parm != null) { if (parm != null) {
parameters = (ICPPASTTemplateParameter[]) ArrayUtil.append( ICPPASTTemplateParameter.class, parameters, ++parametersPos, parm ); fNestedParameters = (ICPPASTTemplateParameter[]) ArrayUtil.append(ICPPASTTemplateParameter.class,
fNestedParameters, parm);
parm.setParent(this); parm.setParent(this);
parm.setPropertyInParent(PARAMETER); parm.setPropertyInParent(PARAMETER);
} }
} }
private ICPPASTTemplateParameter [] parameters = null;
private int parametersPos=-1; public void setIsParameterPack(boolean val) {
private IASTName name; assertNotFrozen();
private IASTExpression defaultValue; fIsParameterPack= val;
}
public boolean isParameterPack() {
return fIsParameterPack;
}
public IASTName getName() { public IASTName getName() {
return name; return fName;
} }
public void setName(IASTName name) { public void setName(IASTName name) {
assertNotFrozen(); assertNotFrozen();
this.name =name; this.fName =name;
if (name != null) { if (name != null) {
name.setParent(this); name.setParent(this);
name.setPropertyInParent(PARAMETER_NAME); name.setPropertyInParent(PARAMETER_NAME);
@ -81,12 +93,12 @@ public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
} }
public IASTExpression getDefaultValue() { public IASTExpression getDefaultValue() {
return defaultValue; return fDefaultValue;
} }
public void setDefaultValue(IASTExpression expression) { public void setDefaultValue(IASTExpression expression) {
assertNotFrozen(); assertNotFrozen();
this.defaultValue = expression; this.fDefaultValue = expression;
if (expression != null) { if (expression != null) {
expression.setParent(this); expression.setParent(this);
expression.setPropertyInParent(DEFAULT_VALUE); expression.setPropertyInParent(DEFAULT_VALUE);
@ -107,8 +119,8 @@ public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
for ( int i = 0; i < ps.length; i++ ) { for ( int i = 0; i < ps.length; i++ ) {
if( !ps[i].accept( action ) ) return false; if( !ps[i].accept( action ) ) return false;
} }
if( name != null ) if( !name.accept( action ) ) return false; if( fName != null ) if( !fName.accept( action ) ) return false;
if( defaultValue != null ) if( !defaultValue.accept( action ) ) return false; if( fDefaultValue != null ) if( !fDefaultValue.accept( action ) ) return false;
if (action.shouldVisitTemplateParameters && action instanceof ICPPASTVisitor) { if (action.shouldVisitTemplateParameters && action instanceof ICPPASTVisitor) {
switch( ((ICPPASTVisitor)action).leave( this ) ){ switch( ((ICPPASTVisitor)action).leave( this ) ){
@ -121,17 +133,17 @@ public class CPPASTTemplatedTypeTemplateParameter extends ASTNode implements
} }
public int getRoleForName(IASTName n) { public int getRoleForName(IASTName n) {
if( n == name ) if( n == fName )
return r_declaration; return r_declaration;
return r_unclear; return r_unclear;
} }
public void replace(IASTNode child, IASTNode other) { public void replace(IASTNode child, IASTNode other) {
if( child == defaultValue ) if( child == fDefaultValue )
{ {
other.setPropertyInParent( child.getPropertyInParent() ); other.setPropertyInParent( child.getPropertyInParent() );
other.setParent( child.getParent() ); other.setParent( child.getParent() );
defaultValue = (IASTExpression) other; fDefaultValue = (IASTExpression) other;
} }
} }
} }

View file

@ -1,28 +1,30 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2004, 2008 IBM Corporation and others. * Copyright (c) 2004, 2009 IBM Corporation 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
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* IBM - Initial API and implementation * John Camelon (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier; import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator; import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeId;
import org.eclipse.cdt.internal.core.dom.parser.ASTNode; import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
/** /**
* @author jcamelon * Type id for c++
*/ */
public class CPPASTTypeId extends ASTNode implements IASTTypeId { public class CPPASTTypeId extends ASTNode implements ICPPASTTypeId {
private IASTDeclSpecifier declSpec; private IASTDeclSpecifier declSpec;
private IASTDeclarator absDecl; private IASTDeclarator absDecl;
private boolean isPackExpansion;
public CPPASTTypeId() { public CPPASTTypeId() {
@ -38,6 +40,7 @@ public class CPPASTTypeId extends ASTNode implements IASTTypeId {
copy.setDeclSpecifier(declSpec == null ? null : declSpec.copy()); copy.setDeclSpecifier(declSpec == null ? null : declSpec.copy());
copy.setAbstractDeclarator(absDecl == null ? null : absDecl.copy()); copy.setAbstractDeclarator(absDecl == null ? null : absDecl.copy());
copy.setOffsetAndLength(this); copy.setOffsetAndLength(this);
copy.isPackExpansion= isPackExpansion;
return copy; return copy;
} }
@ -68,6 +71,14 @@ public class CPPASTTypeId extends ASTNode implements IASTTypeId {
} }
} }
public boolean isPackExpansion() {
return isPackExpansion;
}
public void setIsPackExpansion(boolean val) {
isPackExpansion= val;
}
@Override @Override
public boolean accept( ASTVisitor action ){ public boolean accept( ASTVisitor action ){
if( action.shouldVisitTypeIds ){ if( action.shouldVisitTypeIds ){

View file

@ -205,6 +205,7 @@ public class CPPASTUnaryExpression extends ASTNode implements ICPPASTUnaryExpres
final int op= getOperator(); final int op= getOperator();
switch (op) { switch (op) {
case op_sizeof: case op_sizeof:
case op_sizeofParameterPack:
return CPPVisitor.get_SIZE_T(this); return CPPVisitor.get_SIZE_T(this);
case op_typeid: case op_typeid:
return CPPVisitor.get_type_info(this); return CPPVisitor.get_type_info(this);

View file

@ -107,4 +107,8 @@ public class CPPBuiltinParameter extends PlatformObject implements ICPPParameter
public IValue getInitialValue() { public IValue getInitialValue() {
return null; return null;
} }
public boolean isParameterPack() {
return false;
}
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -32,7 +32,7 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPTemplates;
public class CPPClassInstance extends CPPClassSpecialization implements ICPPTemplateInstance { public class CPPClassInstance extends CPPClassSpecialization implements ICPPTemplateInstance {
private ICPPTemplateArgument[] arguments; private ICPPTemplateArgument[] arguments;
public CPPClassInstance(IBinding owner, ICPPClassType orig, CPPTemplateParameterMap argMap, ICPPTemplateArgument[] args) { public CPPClassInstance(ICPPClassType orig, IBinding owner, CPPTemplateParameterMap argMap, ICPPTemplateArgument[] args) {
super(orig, owner, argMap); super(orig, owner, argMap);
this.arguments= args; this.arguments= args;
} }

View file

@ -277,7 +277,7 @@ public class CPPClassTemplate extends CPPTemplateDefinition implements ICPPClass
return false; return false;
} }
public ICPPDeferredClassInstance asDeferredInstance() throws DOMException { public final ICPPDeferredClassInstance asDeferredInstance() throws DOMException {
if (fDeferredInstance == null) { if (fDeferredInstance == null) {
fDeferredInstance= createDeferredInstance(); fDeferredInstance= createDeferredInstance();
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2007, 2008 QNX Software Systems and others. * Copyright (c) 2007, 2009 QNX Software Systems 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
@ -21,9 +21,9 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
*/ */
public class CPPConstructorInstance extends CPPMethodInstance implements ICPPConstructor { public class CPPConstructorInstance extends CPPMethodInstance implements ICPPConstructor {
public CPPConstructorInstance(ICPPClassType owner, ICPPConstructor orig, public CPPConstructorInstance(ICPPConstructor orig, ICPPClassType owner,
CPPTemplateParameterMap tpmap, ICPPTemplateArgument[] args) { CPPTemplateParameterMap tpmap, ICPPTemplateArgument[] args) {
super(owner, orig, tpmap, args); super(orig, owner, tpmap, args);
} }
public boolean isExplicit() throws DOMException { public boolean isExplicit() throws DOMException {

View file

@ -1,5 +1,5 @@
/************************************************************************* /*************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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,7 +12,6 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; 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.ICPPConstructor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
@ -23,7 +22,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
public class CPPConstructorSpecialization extends CPPMethodSpecialization public class CPPConstructorSpecialization extends CPPMethodSpecialization
implements ICPPConstructor { implements ICPPConstructor {
public CPPConstructorSpecialization(IBinding orig, ICPPClassType owner, public CPPConstructorSpecialization(ICPPConstructor orig, ICPPClassType owner,
ICPPTemplateParameterMap argMap) { ICPPTemplateParameterMap argMap) {
super(orig, owner, argMap); super(orig, owner, argMap);
} }

View file

@ -1,5 +1,5 @@
/************************************************************************* /*************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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,7 +12,6 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; 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.ICPPConstructor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
@ -23,9 +22,9 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
public class CPPConstructorTemplateSpecialization extends CPPMethodTemplateSpecialization public class CPPConstructorTemplateSpecialization extends CPPMethodTemplateSpecialization
implements ICPPConstructor { implements ICPPConstructor {
public CPPConstructorTemplateSpecialization(IBinding specialized, public CPPConstructorTemplateSpecialization(ICPPConstructor original,
ICPPClassType owner, ICPPTemplateParameterMap tpmap) { ICPPClassType owner, ICPPTemplateParameterMap tpmap) {
super(specialized, owner, tpmap); super(original, owner, tpmap);
} }
/* (non-Javadoc) /* (non-Javadoc)

View file

@ -48,6 +48,7 @@ import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries; import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding; import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
import org.eclipse.core.runtime.PlatformObject; import org.eclipse.core.runtime.PlatformObject;
/** /**
@ -107,6 +108,15 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
public IType[] getExceptionSpecification() throws DOMException { public IType[] getExceptionSpecification() throws DOMException {
throw new DOMException(this); throw new DOMException(this);
} }
public int getRequiredArgumentCount() throws DOMException {
throw new DOMException(this);
}
public boolean hasParameterPack() {
return false;
}
public boolean hasSameFunctionParameterTypeList(ICPPFunction function) {
return false;
}
} }
protected IASTDeclarator[] declarations; protected IASTDeclarator[] declarations;
@ -574,4 +584,29 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
} }
return null; return null;
} }
public int getRequiredArgumentCount() throws DOMException {
return getRequiredArgumentCount(getParameters());
}
public static int getRequiredArgumentCount(ICPPParameter[] pars) throws DOMException {
int result= pars.length;
while(result > 0) {
final ICPPParameter p = pars[result-1];
if (p.hasDefaultValue() || p.isParameterPack()) {
result--;
} else {
if (pars.length == 1 && SemanticUtil.isVoidType(p.getType())) {
return 0;
}
return result;
}
}
return 0;
}
public boolean hasParameterPack() {
ICPPParameter[] pars= getParameters();
return pars.length > 0 && pars[pars.length-1].isParameterPack();
}
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -29,7 +29,7 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPTemplates;
public class CPPFunctionInstance extends CPPFunctionSpecialization implements ICPPTemplateInstance { public class CPPFunctionInstance extends CPPFunctionSpecialization implements ICPPTemplateInstance {
private ICPPTemplateArgument[] fArguments; private ICPPTemplateArgument[] fArguments;
public CPPFunctionInstance(IBinding owner, ICPPFunction orig, CPPTemplateParameterMap argMap, ICPPTemplateArgument[] args) { public CPPFunctionInstance(ICPPFunction orig, IBinding owner, CPPTemplateParameterMap argMap, ICPPTemplateArgument[] args) {
super(orig, owner, argMap); super(orig, owner, argMap);
fArguments = args; fArguments = args;
} }

View file

@ -40,10 +40,10 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
*/ */
public class CPPFunctionSpecialization extends CPPSpecialization implements ICPPFunction, ICPPInternalFunction { public class CPPFunctionSpecialization extends CPPSpecialization implements ICPPFunction, ICPPInternalFunction {
private ICPPFunctionType type = null; private ICPPFunctionType type = null;
private ICPPParameter[] specializedParams = null; private ICPPParameter[] fParams = null;
private IType[] specializedExceptionSpec = null; private IType[] specializedExceptionSpec = null;
public CPPFunctionSpecialization(IBinding orig, IBinding owner, ICPPTemplateParameterMap argMap) { public CPPFunctionSpecialization(ICPPFunction orig, IBinding owner, ICPPTemplateParameterMap argMap) {
super(orig, owner, argMap); super(orig, owner, argMap);
} }
@ -52,25 +52,38 @@ public class CPPFunctionSpecialization extends CPPSpecialization implements ICPP
} }
public ICPPParameter[] getParameters() throws DOMException { public ICPPParameter[] getParameters() throws DOMException {
if (specializedParams == null) { if (fParams == null) {
ICPPFunction function = (ICPPFunction) getSpecializedBinding(); ICPPFunction function = getFunction();
ICPPParameter[] params = function.getParameters(); ICPPParameter[] params = function.getParameters();
specializedParams = new ICPPParameter[params.length]; if (params.length == 0) {
for (int i = 0; i < params.length; i++) { fParams= params;
specializedParams[i] = new CPPParameterSpecialization(params[i], } else {
this, getTemplateParameterMap()); // Because of parameter packs there can be more or less parameters in the specialization
final ICPPTemplateParameterMap tparMap = getTemplateParameterMap();
IType[] ptypes= getType().getParameterTypes();
final int length = ptypes.length;
ICPPParameter par= null;
fParams = new ICPPParameter[length];
for (int i = 0; i < length; i++) {
if (i < params.length) {
par= params[i];
} // else reuse last parameter (which should be a pack)
fParams[i] = new CPPParameterSpecialization(par, this, ptypes[i], tparMap);
} }
} }
return specializedParams; }
return fParams;
}
public int getRequiredArgumentCount() throws DOMException {
return ((ICPPFunction) getSpecializedBinding()).getRequiredArgumentCount();
}
public boolean hasParameterPack() {
return ((ICPPFunction) getSpecializedBinding()).hasParameterPack();
} }
public IScope getFunctionScope() { public IScope getFunctionScope() {
// resolveAllDeclarations();
// if (definition != null) {
// return definition.getFunctionScope();
// }
//
// return declarations[0].getFunctionScope();
return null; return null;
} }

View file

@ -103,6 +103,12 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
public IType[] getExceptionSpecification() throws DOMException { public IType[] getExceptionSpecification() throws DOMException {
throw new DOMException( this ); throw new DOMException( this );
} }
public int getRequiredArgumentCount() throws DOMException {
throw new DOMException( this );
}
public boolean hasParameterPack() {
return false;
}
} }
protected ICPPFunctionType type = null; protected ICPPFunctionType type = null;
@ -176,6 +182,16 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
return CPPBuiltinParameter.createParameterList(getType()); return CPPBuiltinParameter.createParameterList(getType());
} }
public int getRequiredArgumentCount() throws DOMException {
return CPPFunction.getRequiredArgumentCount(getParameters());
}
public boolean hasParameterPack() {
ICPPParameter[] pars= getParameters();
return pars.length > 0 && pars[pars.length-1].isParameterPack();
}
public IScope getFunctionScope() { public IScope getFunctionScope() {
return null; return null;
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -15,6 +15,7 @@ import org.eclipse.cdt.core.dom.ast.ASTTypeUtil;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunction;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionTemplate; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionTemplate;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance;
@ -30,8 +31,8 @@ public class CPPFunctionTemplateSpecialization extends CPPFunctionSpecialization
private ObjectMap instances = null; private ObjectMap instances = null;
public CPPFunctionTemplateSpecialization(IBinding specialized, ICPPClassType owner, ICPPTemplateParameterMap argumentMap) { public CPPFunctionTemplateSpecialization(ICPPFunction original, ICPPClassType owner, ICPPTemplateParameterMap argumentMap) {
super(specialized, owner, argumentMap); super(original, owner, argumentMap);
} }
public ICPPTemplateParameter[] getTemplateParameters() throws DOMException { public ICPPTemplateParameter[] getTemplateParameters() throws DOMException {

View file

@ -12,11 +12,9 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTTypeUtil; import org.eclipse.cdt.core.dom.ast.ASTTypeUtil;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IPointerType; import org.eclipse.cdt.core.dom.ast.IPointerType;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.ITypedef; import org.eclipse.cdt.core.dom.ast.ITypedef;
import org.eclipse.cdt.core.dom.ast.IBasicType.Kind;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.internal.core.dom.parser.ISerializableType; import org.eclipse.cdt.internal.core.dom.parser.ISerializableType;
import org.eclipse.cdt.internal.core.dom.parser.ITypeMarshalBuffer; import org.eclipse.cdt.internal.core.dom.parser.ITypeMarshalBuffer;
@ -31,6 +29,7 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
private IType returnType; private IType returnType;
private boolean isConst; private boolean isConst;
private boolean isVolatile; private boolean isVolatile;
private boolean takesVarargs;
/** /**
* @param returnType * @param returnType
@ -41,11 +40,13 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
this.parameters = types; this.parameters = types;
} }
public CPPFunctionType(IType returnType, IType[] types, boolean isConst, boolean isVolatile) { public CPPFunctionType(IType returnType, IType[] types, boolean isConst, boolean isVolatile,
boolean takesVarargs) {
this.returnType = returnType; this.returnType = returnType;
this.parameters = types; this.parameters = types;
this.isConst = isConst; this.isConst = isConst;
this.isVolatile= isVolatile; this.isVolatile= isVolatile;
this.takesVarargs= takesVarargs;
} }
public boolean isSameType(IType o) { public boolean isSameType(IType o) {
@ -53,6 +54,10 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
return o.isSameType(this); return o.isSameType(this);
if (o instanceof ICPPFunctionType) { if (o instanceof ICPPFunctionType) {
ICPPFunctionType ft = (ICPPFunctionType) o; ICPPFunctionType ft = (ICPPFunctionType) o;
if (isConst() != ft.isConst() || isVolatile() != ft.isVolatile() || takesVarArgs() != ft.takesVarArgs()) {
return false;
}
IType[] fps; IType[] fps;
fps = ft.getParameterTypes(); fps = ft.getParameterTypes();
//constructors & destructors have null return type //constructors & destructors have null return type
@ -62,12 +67,10 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
return false; return false;
if (parameters.length == 1 && fps.length == 0) { if (parameters.length == 1 && fps.length == 0) {
IType p0= SemanticUtil.getNestedType(parameters[0], SemanticUtil.TDEF); if (!SemanticUtil.isVoidType(parameters[0]))
if (!(p0 instanceof IBasicType) || ((IBasicType) p0).getKind() != Kind.eVoid)
return false; return false;
} else if (fps.length == 1 && parameters.length == 0) { } else if (fps.length == 1 && parameters.length == 0) {
IType p0= SemanticUtil.getNestedType(fps[0], SemanticUtil.TDEF); if (!SemanticUtil.isVoidType(fps[0]))
if (!(p0 instanceof IBasicType) || ((IBasicType) p0).getKind() != Kind.eVoid)
return false; return false;
} else if (parameters.length != fps.length) { } else if (parameters.length != fps.length) {
return false; return false;
@ -78,10 +81,6 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
} }
} }
if (isConst() != ft.isConst() || isVolatile() != ft.isVolatile()) {
return false;
}
return true; return true;
} }
return false; return false;
@ -125,6 +124,10 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
return isVolatile; return isVolatile;
} }
public boolean takesVarArgs() {
return takesVarargs;
}
@Override @Override
public String toString() { public String toString() {
return ASTTypeUtil.getType(this); return ASTTypeUtil.getType(this);
@ -134,10 +137,11 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
int firstByte= ITypeMarshalBuffer.FUNCTION_TYPE; int firstByte= ITypeMarshalBuffer.FUNCTION_TYPE;
if (isConst()) firstByte |= ITypeMarshalBuffer.FLAG1; if (isConst()) firstByte |= ITypeMarshalBuffer.FLAG1;
if (isVolatile()) firstByte |= ITypeMarshalBuffer.FLAG2; if (isVolatile()) firstByte |= ITypeMarshalBuffer.FLAG2;
if (takesVarArgs()) firstByte |= ITypeMarshalBuffer.FLAG3;
int len= (parameters.length & 0xffff); int len= (parameters.length & 0xffff);
if (len > 0xff) { if (len > 0xff) {
firstByte |= ITypeMarshalBuffer.FLAG3; firstByte |= ITypeMarshalBuffer.FLAG4;
buffer.putByte((byte) firstByte); buffer.putByte((byte) firstByte);
buffer.putShort((short) len); buffer.putShort((short) len);
} else { } else {
@ -153,7 +157,7 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
public static IType unmarshal(int firstByte, ITypeMarshalBuffer buffer) throws CoreException { public static IType unmarshal(int firstByte, ITypeMarshalBuffer buffer) throws CoreException {
int len; int len;
if (((firstByte & ITypeMarshalBuffer.FLAG3) != 0)) { if (((firstByte & ITypeMarshalBuffer.FLAG4) != 0)) {
len= buffer.getShort(); len= buffer.getShort();
} else { } else {
len= buffer.getByte(); len= buffer.getByte();
@ -164,6 +168,6 @@ public class CPPFunctionType implements ICPPFunctionType, ISerializableType {
pars[i]= buffer.unmarshalType(); pars[i]= buffer.unmarshalType();
} }
return new CPPFunctionType(rt, pars, (firstByte & ITypeMarshalBuffer.FLAG1) != 0, return new CPPFunctionType(rt, pars, (firstByte & ITypeMarshalBuffer.FLAG1) != 0,
(firstByte & ITypeMarshalBuffer.FLAG2) != 0); (firstByte & ITypeMarshalBuffer.FLAG2) != 0, (firstByte & ITypeMarshalBuffer.FLAG3) != 0);
} }
} }

View file

@ -19,11 +19,9 @@ import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration; import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IBasicType.Kind;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateDeclaration;
@ -37,6 +35,7 @@ import org.eclipse.cdt.core.parser.util.CharArrayUtils;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal; import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries; import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
/** /**
* Binding for implicit methods, base class for implicit constructors. * Binding for implicit methods, base class for implicit constructors.
@ -139,9 +138,7 @@ public class CPPImplicitMethod extends CPPImplicitFunction implements ICPPMethod
ok = idx == ps.length; ok = idx == ps.length;
} else if (ps.length == 0) { } else if (ps.length == 0) {
if (params.length == 1) { if (params.length == 1) {
IType t1 = params[0]; ok = SemanticUtil.isVoidType(params[0]);
ok = (t1 instanceof IBasicType)
&& ((IBasicType) t1).getKind() == Kind.eVoid;
} }
} }
} else { } else {

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -21,8 +21,8 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
*/ */
public class CPPMethodInstance extends CPPFunctionInstance implements ICPPMethod { public class CPPMethodInstance extends CPPFunctionInstance implements ICPPMethod {
public CPPMethodInstance(ICPPClassType owner, ICPPMethod orig, CPPTemplateParameterMap tpmap, ICPPTemplateArgument[] args) { public CPPMethodInstance(ICPPMethod orig, ICPPClassType owner, CPPTemplateParameterMap tpmap, ICPPTemplateArgument[] args) {
super(owner, orig, tpmap, args); super(orig, owner, tpmap, args);
} }
/* (non-Javadoc) /* (non-Javadoc)

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -16,7 +16,6 @@ import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition; import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration; import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
@ -29,7 +28,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
public class CPPMethodSpecialization extends CPPFunctionSpecialization public class CPPMethodSpecialization extends CPPFunctionSpecialization
implements ICPPMethod { implements ICPPMethod {
public CPPMethodSpecialization(IBinding orig, ICPPClassType owner, ICPPTemplateParameterMap argMap ) { public CPPMethodSpecialization(ICPPMethod orig, ICPPClassType owner, ICPPTemplateParameterMap argMap ) {
super(orig, owner, argMap ); super(orig, owner, argMap );
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2005, 2008 IBM Corporation and others. * Copyright (c) 2005, 2009 IBM Corporation 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
@ -23,7 +23,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
public class CPPMethodTemplateSpecialization extends CPPFunctionTemplateSpecialization public class CPPMethodTemplateSpecialization extends CPPFunctionTemplateSpecialization
implements ICPPMethod { implements ICPPMethod {
public CPPMethodTemplateSpecialization(IBinding specialized, ICPPClassType owner, public CPPMethodTemplateSpecialization(ICPPMethod specialized, ICPPClassType owner,
ICPPTemplateParameterMap ctmap) { ICPPTemplateParameterMap ctmap) {
super(specialized, owner, ctmap); super(specialized, owner, ctmap);
} }

View file

@ -12,7 +12,6 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.IASTASMDeclaration; import org.eclipse.cdt.core.dom.ast.IASTASMDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTArrayDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTArrayModifier; import org.eclipse.cdt.core.dom.ast.IASTArrayModifier;
import org.eclipse.cdt.core.dom.ast.IASTBreakStatement; import org.eclipse.cdt.core.dom.ast.IASTBreakStatement;
import org.eclipse.cdt.core.dom.ast.IASTCaseStatement; import org.eclipse.cdt.core.dom.ast.IASTCaseStatement;
@ -28,13 +27,10 @@ import org.eclipse.cdt.core.dom.ast.IASTDoStatement;
import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier; import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTExpressionStatement; import org.eclipse.cdt.core.dom.ast.IASTExpressionStatement;
import org.eclipse.cdt.core.dom.ast.IASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTGotoStatement; import org.eclipse.cdt.core.dom.ast.IASTGotoStatement;
import org.eclipse.cdt.core.dom.ast.IASTIdExpression; import org.eclipse.cdt.core.dom.ast.IASTIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializer; import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializerList;
import org.eclipse.cdt.core.dom.ast.IASTLabelStatement; import org.eclipse.cdt.core.dom.ast.IASTLabelStatement;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNullStatement; import org.eclipse.cdt.core.dom.ast.IASTNullStatement;
@ -50,6 +46,7 @@ import org.eclipse.cdt.core.dom.ast.IASTStatement;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.IASTTypeIdInitializerExpression; import org.eclipse.cdt.core.dom.ast.IASTTypeIdInitializerExpression;
import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator; import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTArrayDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTArraySubscriptExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTArraySubscriptExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTBinaryExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTBinaryExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCastExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCastExpression;
@ -58,10 +55,12 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExpressionList; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExpressionList;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionCallExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionCallExpression;
@ -69,6 +68,8 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionWithTryBlock; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionWithTryBlock;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTIfStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTIfStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerList;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLiteralExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLiteralExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier;
@ -76,6 +77,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceAlias;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceDefinition; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNewExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNewExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTOperatorName; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTOperatorName;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPackExpansionExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPointerToMember; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTPointerToMember;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTQualifiedName; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTQualifiedName;
@ -91,6 +93,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTranslationUnit; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTranslationUnit;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTryBlockStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTryBlockStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeIdExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeIdExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUnaryExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUnaryExpression;
@ -324,11 +327,11 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
return new CPPASTTypeIdExpression(operator, typeId); return new CPPASTTypeIdExpression(operator, typeId);
} }
public IASTDeclarator newDeclarator(IASTName name) { public ICPPASTDeclarator newDeclarator(IASTName name) {
return new CPPASTDeclarator(name); return new CPPASTDeclarator(name);
} }
public IASTTypeId newTypeId(IASTDeclSpecifier declSpecifier, IASTDeclarator declarator) { public ICPPASTTypeId newTypeId(IASTDeclSpecifier declSpecifier, IASTDeclarator declarator) {
return new CPPASTTypeId(declSpecifier, declarator); return new CPPASTTypeId(declSpecifier, declarator);
} }
@ -340,7 +343,7 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
return new CPPASTSimpleDeclaration(declSpecifier); return new CPPASTSimpleDeclaration(declSpecifier);
} }
public IASTInitializerExpression newInitializerExpression(IASTExpression expression) { public ICPPASTInitializerExpression newInitializerExpression(IASTExpression expression) {
return new CPPASTInitializerExpression(expression); return new CPPASTInitializerExpression(expression);
} }
@ -469,7 +472,7 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
return new GPPASTPointerToMember(name); return new GPPASTPointerToMember(name);
} }
public IASTInitializerList newInitializerList() { public ICPPASTInitializerList newInitializerList() {
return new CPPASTInitializerList(); return new CPPASTInitializerList();
} }
@ -481,7 +484,7 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
return new CPPASTArrayModifier(expr); return new CPPASTArrayModifier(expr);
} }
public IASTArrayDeclarator newArrayDeclarator(IASTName name) { public ICPPASTArrayDeclarator newArrayDeclarator(IASTName name) {
return new CPPASTArrayDeclarator(name); return new CPPASTArrayDeclarator(name);
} }
@ -498,7 +501,7 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
return new CPPASTFunctionWithTryBlock(declSpecifier, declarator, bodyStatement); return new CPPASTFunctionWithTryBlock(declSpecifier, declarator, bodyStatement);
} }
public IASTFieldDeclarator newFieldDeclarator(IASTName name, IASTExpression bitFieldSize) { public ICPPASTFieldDeclarator newFieldDeclarator(IASTName name, IASTExpression bitFieldSize) {
return new CPPASTFieldDeclarator(name, bitFieldSize); return new CPPASTFieldDeclarator(name, bitFieldSize);
} }
@ -522,4 +525,8 @@ public class CPPNodeFactory extends NodeFactory implements ICPPNodeFactory {
ICPPASTLiteralExpression message) { ICPPASTLiteralExpression message) {
return new CPPASTStaticAssertionDeclaration(condition, message); return new CPPASTStaticAssertionDeclaration(condition, message);
} }
public ICPPASTPackExpansionExpression newPackExpansionExpression(IASTExpression pattern) {
return new CPPASTPackExpansionExpression(pattern);
}
} }

View file

@ -26,6 +26,8 @@ import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IScope; import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IValue; import org.eclipse.cdt.core.dom.ast.IValue;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.CharArrayUtils; import org.eclipse.cdt.core.parser.util.CharArrayUtils;
@ -34,7 +36,6 @@ import org.eclipse.cdt.internal.core.dom.parser.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries; import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding; import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
import org.eclipse.core.runtime.PlatformObject; import org.eclipse.core.runtime.PlatformObject;
/** /**
@ -81,28 +82,35 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
public IValue getInitialValue() { public IValue getInitialValue() {
return null; return null;
} }
public boolean isParameterPack() {
return false;
}
} }
private IType type = null; private IType fType = null;
private IASTName[] declarations = null; private IASTName[] fDeclarations = null;
private int fPosition; private int fPosition;
public CPPParameter(IASTName name, int pos) { public CPPParameter(IASTName name, int pos) {
this.declarations = new IASTName[] { name }; this.fDeclarations = new IASTName[] { name };
fPosition= pos; fPosition= pos;
} }
public CPPParameter(IType type, int pos) { public CPPParameter(IType type, int pos) {
this.type = type; this.fType = type;
fPosition= pos; fPosition= pos;
} }
public boolean isParameterPack() {
return getType() instanceof ICPPParameterPackType;
}
/* (non-Javadoc) /* (non-Javadoc)
* @see org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPBinding#getDeclarations() * @see org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPBinding#getDeclarations()
*/ */
public IASTNode[] getDeclarations() { public IASTNode[] getDeclarations() {
return declarations; return fDeclarations;
} }
/* (non-Javadoc) /* (non-Javadoc)
@ -116,29 +124,29 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
if (!(node instanceof IASTName)) if (!(node instanceof IASTName))
return; return;
IASTName name = (IASTName) node; IASTName name = (IASTName) node;
if (declarations == null) { if (fDeclarations == null) {
declarations = new IASTName[] { name }; fDeclarations = new IASTName[] { name };
} else { } else {
//keep the lowest offset declaration in[0] //keep the lowest offset declaration in[0]
if (declarations.length > 0 && ((ASTNode)node).getOffset() < ((ASTNode)declarations[0]).getOffset()) { if (fDeclarations.length > 0 && ((ASTNode)node).getOffset() < ((ASTNode)fDeclarations[0]).getOffset()) {
declarations = (IASTName[]) ArrayUtil.prepend(IASTName.class, declarations, name); fDeclarations = (IASTName[]) ArrayUtil.prepend(IASTName.class, fDeclarations, name);
} else { } else {
declarations = (IASTName[]) ArrayUtil.append(IASTName.class, declarations, name); fDeclarations = (IASTName[]) ArrayUtil.append(IASTName.class, fDeclarations, name);
} }
} }
} }
private IASTName getPrimaryDeclaration() { private IASTName getPrimaryDeclaration() {
if (declarations != null) { if (fDeclarations != null) {
for (int i = 0; i < declarations.length && declarations[i] != null; i++) { for (int i = 0; i < fDeclarations.length && fDeclarations[i] != null; i++) {
IASTNode node = declarations[i].getParent(); IASTNode node = fDeclarations[i].getParent();
while (!(node instanceof IASTDeclaration)) while (!(node instanceof IASTDeclaration))
node = node.getParent(); node = node.getParent();
if (node instanceof IASTFunctionDefinition) if (node instanceof IASTFunctionDefinition)
return declarations[i]; return fDeclarations[i];
} }
return declarations[0]; return fDeclarations[0];
} }
return null; return null;
} }
@ -170,8 +178,8 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
* @see org.eclipse.cdt.core.dom.ast.IBinding#getPhysicalNode() * @see org.eclipse.cdt.core.dom.ast.IBinding#getPhysicalNode()
*/ */
public IASTNode getPhysicalNode() { public IASTNode getPhysicalNode() {
if (declarations != null) if (fDeclarations != null)
return declarations[0]; return fDeclarations[0];
return null; return null;
} }
@ -179,11 +187,17 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
* @see org.eclipse.cdt.core.dom.ast.IVariable#getType() * @see org.eclipse.cdt.core.dom.ast.IVariable#getType()
*/ */
public IType getType() { public IType getType() {
if (type == null && declarations != null) { if (fType == null && fDeclarations != null) {
IType t= CPPVisitor.createType((IASTDeclarator) declarations[0].getParent()); IASTNode parent= fDeclarations[0].getParent();
type= SemanticUtil.adjustParameterType(t, false); while (parent != null) {
if (parent instanceof ICPPASTParameterDeclaration) {
fType= CPPVisitor.createParameterType((ICPPASTParameterDeclaration) parent, false);
break;
} }
return type; parent= parent.getParent();
}
}
return fType;
} }
/* (non-Javadoc) /* (non-Javadoc)
@ -268,10 +282,10 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
} }
public IASTInitializer getDefaultValue() { public IASTInitializer getDefaultValue() {
if (declarations == null) if (fDeclarations == null)
return null; return null;
for (int i = 0; i < declarations.length && declarations[i] != null; i++) { for (int i = 0; i < fDeclarations.length && fDeclarations[i] != null; i++) {
IASTNode parent = declarations[i].getParent(); IASTNode parent = fDeclarations[i].getParent();
while (parent.getPropertyInParent() == IASTDeclarator.NESTED_DECLARATOR) while (parent.getPropertyInParent() == IASTDeclarator.NESTED_DECLARATOR)
parent = parent.getParent(); parent = parent.getParent();
IASTInitializer init = ((IASTDeclarator)parent).getInitializer(); IASTInitializer init = ((IASTDeclarator)parent).getInitializer();
@ -300,7 +314,7 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
} }
public IBinding getOwner() throws DOMException { public IBinding getOwner() throws DOMException {
return CPPVisitor.findEnclosingFunction(declarations[0]); return CPPVisitor.findEnclosingFunction(fDeclarations[0]);
} }
public IValue getInitialValue() { public IValue getInitialValue() {

View file

@ -0,0 +1,77 @@
/*******************************************************************************
* Copyright (c) 2009 Wind River Systems, Inc. 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:
* Markus Schorn (Wind River Systems) - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ast.ASTTypeUtil;
import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.ITypedef;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.ISerializableType;
import org.eclipse.cdt.internal.core.dom.parser.ITypeContainer;
import org.eclipse.cdt.internal.core.dom.parser.ITypeMarshalBuffer;
import org.eclipse.core.runtime.CoreException;
public class CPPParameterPackType implements ICPPParameterPackType, ITypeContainer, ISerializableType {
private IType fType = null;
public CPPParameterPackType(IType type) {
setType(type);
}
public IType getType() {
return fType;
}
public void setType(IType t) {
fType= t;
}
public boolean isSameType(IType obj) {
if (obj == this)
return true;
if (obj instanceof ITypedef)
return ((ITypedef)obj).isSameType(this);
if (obj instanceof ICPPParameterPackType) {
final ICPPParameterPackType rhs = (ICPPParameterPackType) obj;
IType t1= getType();
IType t2= rhs.getType();
return t1 != null && t1.isSameType(t2);
}
return false;
}
@Override
public Object clone() {
try {
return super.clone();
} catch (CloneNotSupportedException e) {
// not going to happen
return null;
}
}
@Override
public String toString() {
return ASTTypeUtil.getType(this);
}
public void marshal(ITypeMarshalBuffer buffer) throws CoreException {
int firstByte= ITypeMarshalBuffer.PACK_EXPANSION;
buffer.putByte((byte) firstByte);
buffer.marshalType(getType());
}
public static IType unmarshal(int firstByte, ITypeMarshalBuffer buffer) throws CoreException {
IType nested= buffer.unmarshalType();
return new CPPParameterPackType(nested);
}
}

View file

@ -15,19 +15,19 @@ import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IValue; import org.eclipse.cdt.core.dom.ast.IValue;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPTemplates;
/** /**
* Binding for a specialization of a parameter. * Binding for a specialization of a parameter.
*/ */
public class CPPParameterSpecialization extends CPPSpecialization implements ICPPParameter { public class CPPParameterSpecialization extends CPPSpecialization implements ICPPParameter {
private IType type = null; private IType fType;
public CPPParameterSpecialization(ICPPParameter orig, IBinding owner, ICPPTemplateParameterMap tpmap) { public CPPParameterSpecialization(ICPPParameter orig, IBinding owner, IType type, ICPPTemplateParameterMap tpmap) {
super(orig, owner, tpmap); super(orig, owner, tpmap);
fType= type;
} }
private ICPPParameter getParameter(){ private ICPPParameter getParameter(){
@ -38,25 +38,17 @@ public class CPPParameterSpecialization extends CPPSpecialization implements ICP
* @see org.eclipse.cdt.core.dom.ast.IVariable#getType() * @see org.eclipse.cdt.core.dom.ast.IVariable#getType()
*/ */
public IType getType() throws DOMException { public IType getType() throws DOMException {
if( type == null ){ return fType;
type= specializeType(getParameter().getType());
} }
return type;
public boolean isParameterPack() {
return fType instanceof ICPPParameterPackType;
} }
@Override @Override
public IType specializeType(IType type) { public IType specializeType(IType type) {
IBinding owner= getOwner(); assert false;
if (owner != null) { return type;
try {
owner= owner.getOwner();
if (owner instanceof ICPPClassSpecialization) {
return CPPTemplates.instantiateType(type, getTemplateParameterMap(), (ICPPClassSpecialization) owner);
}
} catch (DOMException e) {
}
}
return CPPTemplates.instantiateType(type, getTemplateParameterMap(), null);
} }
/* (non-Javadoc) /* (non-Javadoc)

View file

@ -20,6 +20,8 @@ import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IValue; import org.eclipse.cdt.core.dom.ast.IValue;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateNonTypeParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateNonTypeParameter;
import org.eclipse.cdt.internal.core.dom.parser.Value; import org.eclipse.cdt.internal.core.dom.parser.Value;
@ -68,14 +70,23 @@ public class CPPTemplateNonTypeParameter extends CPPTemplateParameter implements
} }
public IType getType() { public IType getType() {
if( type == null ){ if (type == null) {
IASTName name = getPrimaryDeclaration(); IASTNode parent= getPrimaryDeclaration().getParent();
IASTDeclarator dtor = (IASTDeclarator) name.getParent(); while (parent != null) {
type = CPPVisitor.createType( dtor ); if (parent instanceof ICPPASTParameterDeclaration) {
type= CPPVisitor.createParameterType((ICPPASTParameterDeclaration) parent, true);
break;
}
parent= parent.getParent();
}
} }
return type; return type;
} }
public boolean isParameterPack() {
return getType() instanceof ICPPParameterPackType;
}
public boolean isStatic() throws DOMException { public boolean isStatic() throws DOMException {
return false; return false;
} }

View file

@ -50,9 +50,15 @@ public class CPPTemplateTemplateParameter extends CPPTemplateParameter implement
private ICPPTemplateParameter[] templateParameters; private ICPPTemplateParameter[] templateParameters;
private ObjectMap instances; private ObjectMap instances;
private ICPPScope unknownScope; private ICPPScope unknownScope;
private final boolean fIsParameterPack;
public CPPTemplateTemplateParameter(IASTName name) { public CPPTemplateTemplateParameter(IASTName name, boolean isPack) {
super(name); super(name);
fIsParameterPack= isPack;
}
public final boolean isParameterPack() {
return fIsParameterPack;
} }
public ICPPScope asScope() { public ICPPScope asScope() {

View file

@ -29,9 +29,15 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
public class CPPTemplateTypeParameter extends CPPTemplateParameter implements public class CPPTemplateTypeParameter extends CPPTemplateParameter implements
ICPPTemplateTypeParameter, ICPPUnknownType, ICPPUnknownBinding { ICPPTemplateTypeParameter, ICPPUnknownType, ICPPUnknownBinding {
private ICPPScope unknownScope; private ICPPScope unknownScope;
private final boolean fIsParameterPack;
public CPPTemplateTypeParameter(IASTName name) { public CPPTemplateTypeParameter(IASTName name, boolean isPack) {
super(name); super(name);
fIsParameterPack= isPack;
}
public final boolean isParameterPack() {
return fIsParameterPack;
} }
public ICPPScope asScope() { public ICPPScope asScope() {

View file

@ -89,4 +89,12 @@ public class CPPUnknownFunction extends CPPUnknownBinding implements ICPPFunctio
public boolean takesVarArgs() throws DOMException { public boolean takesVarArgs() throws DOMException {
return false; return false;
} }
public int getRequiredArgumentCount() throws DOMException {
return 0;
}
public boolean hasParameterPack() {
return false;
}
} }

View file

@ -29,7 +29,6 @@ import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration; import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IField; import org.eclipse.cdt.core.dom.ast.IField;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
@ -38,7 +37,6 @@ import org.eclipse.cdt.core.dom.ast.IQualifierType;
import org.eclipse.cdt.core.dom.ast.IScope; import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.ITypedef; import org.eclipse.cdt.core.dom.ast.ITypedef;
import org.eclipse.cdt.core.dom.ast.IBasicType.Kind;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclSpecifier; 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.ICPPASTElaboratedTypeSpecifier;
@ -669,8 +667,8 @@ public class ClassTypeHelper {
if (params.length == 0) if (params.length == 0)
return KIND_DEFAULT_CTOR; return KIND_DEFAULT_CTOR;
if (params.length == 1) { if (params.length == 1) {
IType t= params[0]; IType t= SemanticUtil.getNestedType(params[0], SemanticUtil.TDEF);
if (t instanceof IBasicType && ((IBasicType) t).getKind() == Kind.eVoid) if (SemanticUtil.isVoidType(t))
return KIND_DEFAULT_CTOR; return KIND_DEFAULT_CTOR;
if (isRefToConstClass(ct, t)) if (isRefToConstClass(ct, t))

View file

@ -16,6 +16,7 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp; package org.eclipse.cdt.internal.core.dom.parser.cpp;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections;
import java.util.List; import java.util.List;
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.ASTVisitor;
@ -32,18 +33,14 @@ import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator; import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTElaboratedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.IASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionCallExpression; import org.eclipse.cdt.core.dom.ast.IASTFunctionCallExpression;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTIdExpression; import org.eclipse.cdt.core.dom.ast.IASTIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializer; import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression;
import org.eclipse.cdt.core.dom.ast.IASTInitializerList;
import org.eclipse.cdt.core.dom.ast.IASTLiteralExpression; import org.eclipse.cdt.core.dom.ast.IASTLiteralExpression;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNamedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.IASTNamedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTPointer; import org.eclipse.cdt.core.dom.ast.IASTPointer;
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator; import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
import org.eclipse.cdt.core.dom.ast.IASTProblem; import org.eclipse.cdt.core.dom.ast.IASTProblem;
@ -60,6 +57,7 @@ import org.eclipse.cdt.core.dom.ast.IASTWhileStatement;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IScope; import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTAmbiguousTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTAmbiguousTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTArrayDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCastExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCastExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCatchHandler; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCatchHandler;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
@ -67,15 +65,20 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName; 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.ICPPASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionWithTryBlock; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionWithTryBlock;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTIfStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTIfStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTInitializerList;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLiteralExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLiteralExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier;
@ -98,6 +101,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTranslationUnit; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTranslationUnit;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTryBlockStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTryBlockStatement;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeIdExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeIdExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUnaryExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUnaryExpression;
@ -105,6 +109,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTVisibilityLabel; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTVisibilityLabel;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNodeFactory; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNodeFactory;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTTypeIdExpression; import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTTypeIdExpression;
import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTUnaryExpression; import org.eclipse.cdt.core.dom.ast.gnu.IGNUASTUnaryExpression;
import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTExplicitTemplateInstantiation; import org.eclipse.cdt.core.dom.ast.gnu.cpp.IGPPASTExplicitTemplateInstantiation;
@ -129,6 +134,8 @@ import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.AbstractGNUSourceCodeParser; import org.eclipse.cdt.internal.core.dom.parser.AbstractGNUSourceCodeParser;
import org.eclipse.cdt.internal.core.dom.parser.BacktrackException; import org.eclipse.cdt.internal.core.dom.parser.BacktrackException;
import org.eclipse.cdt.internal.core.dom.parser.DeclarationOptions; import org.eclipse.cdt.internal.core.dom.parser.DeclarationOptions;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousDeclarator;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousExpression; import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousExpression;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousStatement; import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguousStatement;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor; import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
@ -140,7 +147,6 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
*/ */
public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
private static final int DEFAULT_PARM_LIST_SIZE = 4; private static final int DEFAULT_PARM_LIST_SIZE = 4;
private static final int DEFAULT_POINTEROPS_LIST_SIZE = 4;
private static final int DEFAULT_CATCH_HANDLER_LIST_SIZE= 4; private static final int DEFAULT_CATCH_HANDLER_LIST_SIZE= 4;
private static enum DtorStrategy {PREFER_FUNCTION, PREFER_NESTED} private static enum DtorStrategy {PREFER_FUNCTION, PREFER_NESTED}
@ -351,6 +357,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
/** /**
* Makes a fast check whether there could be template arguments. * Makes a fast check whether there could be template arguments.
* -1: no, 0: ambiguous, 1: yes
*/ */
private int canBeTemplateArguments(CastExprCtx ctx) throws EndOfFileException, BacktrackException { private int canBeTemplateArguments(CastExprCtx ctx) throws EndOfFileException, BacktrackException {
if (LTcatchEOF(1) != IToken.tLT) if (LTcatchEOF(1) != IToken.tLT)
@ -390,11 +397,11 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
lt1= LTcatchEOF(2); lt1= LTcatchEOF(2);
} }
switch(lt1) { switch(lt1) {
// can be some cast-expression or continuation after template-id // Can be some cast-expression or continuation after template-id
case IToken.tCOLONCOLON: // CT<int>::member case IToken.tCOLONCOLON: // CT<int>::member
case IToken.tLPAREN: // ft<int>(args) case IToken.tLPAREN: // ft<int>(args)
return 0; return 0;
// end of an expression // Start of other expressions (then we can't have a template)
// unary expression // unary expression
case IToken.tMINUS: case IToken.tMINUS:
case IToken.tPLUS: case IToken.tPLUS:
@ -450,6 +457,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
case IToken.tRBRACE: case IToken.tRBRACE:
case IToken.tRBRACKET: case IToken.tRBRACKET:
case IToken.tRPAREN: case IToken.tRPAREN:
case IToken.tELLIPSIS: // pack-expansion
return 1; return 1;
// don't know // don't know
default: default:
@ -505,79 +513,103 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} }
private List<IASTNode> templateArgumentList(boolean isAmbiguous) throws EndOfFileException, BacktrackException { private List<IASTNode> templateArgumentList(boolean isAmbiguous) throws EndOfFileException, BacktrackException {
IToken start = LA(1); int startingOffset = LA(1).getOffset();
int startingOffset = start.getOffset();
int endOffset = 0; int endOffset = 0;
start = null; List<IASTNode> list= null;
List<IASTNode> list = new ArrayList<IASTNode>();
final BinaryExprCtx exprCtx = isAmbiguous ? BinaryExprCtx.eAmbigTmplID : BinaryExprCtx.eTmplID; final BinaryExprCtx exprCtx = isAmbiguous ? BinaryExprCtx.eAmbigTmplID : BinaryExprCtx.eTmplID;
boolean failed = false; boolean needComma= false;
int lt1= LT(1); int lt1= LT(1);
while (lt1 != IToken.tGT && lt1 != IToken.tGT_in_SHIFTR && lt1 != IToken.tEOC) { while (lt1 != IToken.tGT && lt1 != IToken.tGT_in_SHIFTR && lt1 != IToken.tEOC) {
if (needComma) {
if (lt1 != IToken.tCOMMA) {
throwBacktrack(startingOffset, endOffset - startingOffset);
}
consume();
} else {
needComma= true;
}
IASTNode node= templateArgument(exprCtx);
if (list == null) {
list= new ArrayList<IASTNode>();
}
list.add(node);
lt1= LT(1);
}
if (list == null) {
return Collections.emptyList();
}
return list;
}
private IASTNode templateArgument(BinaryExprCtx exprCtx) throws EndOfFileException, BacktrackException {
IToken argStart = mark(); IToken argStart = mark();
IASTTypeId typeId = typeId(DeclarationOptions.TYPEID); final ICPPASTTypeId typeId = typeId(DeclarationOptions.TYPEID);
lt1 = LT(1); final int lt1 = LT(1);
if(typeId != null && (lt1==IToken.tCOMMA || lt1==IToken.tGT || lt1 == IToken.tGT_in_SHIFTR || lt1==IToken.tEOC)) { if (typeId != null
// potentially a type-id - check for id-expression ambiguity && (lt1 == IToken.tCOMMA || lt1 == IToken.tGT || lt1 == IToken.tGT_in_SHIFTR
IToken typeIdEnd= mark(); || lt1 == IToken.tEOC || lt1 == IToken.tELLIPSIS)) {
try { // This is potentially a type-id, now check ambiguity with id-expression
// consider ambiguity with id-expressions, only:
IASTDeclSpecifier declspec= typeId.getDeclSpecifier(); IASTDeclSpecifier declspec= typeId.getDeclSpecifier();
if (!(declspec instanceof IASTNamedTypeSpecifier)) if (declspec instanceof IASTNamedTypeSpecifier) {
throw backtrack;
IASTName name= ((IASTNamedTypeSpecifier) declspec).getName(); IASTName name= ((IASTNamedTypeSpecifier) declspec).getName();
if (!name.contains(typeId)) if (name.contains(typeId)) {
throw backtrack;
// A template-id cannot be used in an id-expression as a template argument // A template-id cannot be used in an id-expression as a template argument
// 5.1-11 A template-id shall be used as an unqualified-id only as specified in // 5.1-11 A template-id shall be used as an unqualified-id only as specified in
// 14.7.2, 14.7, and 14.5.4. // 14.7.2, 14.7, and 14.5.4.
name= name.getLastName(); name= name.getLastName();
if (name instanceof ICPPASTTemplateId) if (!(name instanceof ICPPASTTemplateId)) {
throw backtrack; IToken typeIdEnd= mark();
backup(argStart); backup(argStart);
try {
IASTExpression expression = expression(ExprKind.eAssignment, exprCtx); IASTExpression expression = expression(ExprKind.eAssignment, exprCtx);
if (expression instanceof IASTIdExpression) { if (expression instanceof IASTIdExpression) {
if (mark() != typeIdEnd) if (mark() == typeIdEnd) {
throw backtrack; if (LT(1) == IToken.tELLIPSIS) {
IToken ellipsis= consume();
addPackExpansion(typeId, ellipsis);
expression= addPackExpansion(expression, ellipsis);
}
ICPPASTAmbiguousTemplateArgument ambiguity= createAmbiguousTemplateArgument(); ICPPASTAmbiguousTemplateArgument ambiguity= createAmbiguousTemplateArgument();
ambiguity.addTypeId(typeId); ambiguity.addTypeId(typeId);
ambiguity.addIdExpression((IASTIdExpression) expression); ambiguity.addIdExpression(expression);
list.add(ambiguity); return ambiguity;
} else { }
// prefer the typeId at this stage
throw backtrack;
} }
} catch (BacktrackException e) { } catch (BacktrackException e) {
// no ambiguity - its a type-id // Use the typeId
list.add(typeId); }
backup(typeIdEnd); backup(typeIdEnd);
} }
} else { }
// not a type-id - try as expression }
// There is no ambiguity, use the type-id
if (LT(1) == IToken.tELLIPSIS) {
addPackExpansion(typeId, consume());
}
return typeId;
}
// Not a type-id, parse as expression
backup(argStart); backup(argStart);
IASTExpression expression = expression(ExprKind.eAssignment, exprCtx); IASTExpression expr= expression(ExprKind.eAssignment, exprCtx);
list.add(expression); if (LT(1) == IToken.tELLIPSIS) {
expr= addPackExpansion(expr, consume());
}
return expr;
} }
lt1= LT(1); private void addPackExpansion(ICPPASTTypeId typeId, IToken consume) {
if (lt1 == IToken.tCOMMA) { final int endOffset= consume.getEndOffset();
consume(); adjustEndOffset(typeId, endOffset);
lt1= LT(1); typeId.setIsPackExpansion(true);
} else if (lt1 != IToken.tGT && lt1 != IToken.tGT_in_SHIFTR && lt1 != IToken.tEOC) {
failed = true;
endOffset = LA(1).getEndOffset();
break;
} }
}
if (failed)
throwBacktrack(startingOffset, endOffset - startingOffset);
return list; private IASTExpression addPackExpansion(IASTExpression expr, IToken ellipsis) {
IASTExpression result= nodeFactory.newPackExpansionExpression(expr);
return setRange(result, expr, ellipsis.getEndOffset());
} }
private IASTName operatorId() throws BacktrackException, EndOfFileException { private IASTName operatorId() throws BacktrackException, EndOfFileException {
@ -705,6 +737,18 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
allowThrow= true; allowThrow= true;
break; break;
case IToken.tELLIPSIS:
if ((!allowComma && conditionCount == 0))
break loop;
// Precedence: To the left just stronger than ',', to the right no other choice.
lastOperator= new BinaryOperator(lastOperator, expr, lt1, 12, Integer.MAX_VALUE);
expr= nodeFactory.newPackExpansionExpression(null);
setRange(expr, 0, consume().getEndOffset());
if (LT(1) == IToken.tCOMMA)
continue loop;
break loop;
case IToken.tCOMMA: case IToken.tCOMMA:
allowThrow= true; allowThrow= true;
if (!allowComma && conditionCount == 0) if (!allowComma && conditionCount == 0)
@ -1024,6 +1068,23 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
return postfixExpression(ctx); return postfixExpression(ctx);
} }
case IToken.t_sizeof: case IToken.t_sizeof:
if (LTcatchEOF(2) == IToken.tELLIPSIS) {
int offset= consume().getOffset(); // sizeof
consume(); // ...
consume(IToken.tLPAREN); // (
IASTName id= identifier();
IASTIdExpression idexpr= nodeFactory.newIdExpression(id);
setRange(idexpr, id);
IASTUnaryExpression expr= nodeFactory.newUnaryExpression(IASTUnaryExpression.op_sizeofParameterPack, idexpr);
final int lt1= LT(1);
if (lt1 == IToken.tEOC) {
setRange(expr, offset, calculateEndOffset(id));
} else {
final int endOffset = consume(IToken.tRPAREN).getEndOffset(); // )
setRange(expr, offset, endOffset);
}
return expr;
}
return parseTypeidInParenthesisOrUnaryExpression(false, consume().getOffset(), return parseTypeidInParenthesisOrUnaryExpression(false, consume().getOffset(),
IASTTypeIdExpression.op_sizeof, IASTUnaryExpression.op_sizeof, ctx); IASTTypeIdExpression.op_sizeof, IASTUnaryExpression.op_sizeof, ctx);
case IGCCToken.t_typeof: case IGCCToken.t_typeof:
@ -1628,63 +1689,81 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
final int lt1= LT(1); final int lt1= LT(1);
if (lt1 == IToken.tGT || lt1 == IToken.tEOC || lt1 == IToken.tGT_in_SHIFTR) if (lt1 == IToken.tGT || lt1 == IToken.tEOC || lt1 == IToken.tGT_in_SHIFTR)
return returnValue; return returnValue;
final int offset = LA(1).getOffset();
if (lt1 == IToken.t_class || lt1 == IToken.t_typename) { if (lt1 == IToken.t_class || lt1 == IToken.t_typename) {
IToken startingToken = LA(1);
int lastOffset = 0;
int type = (lt1 == IToken.t_class ? ICPPASTSimpleTypeTemplateParameter.st_class int type = (lt1 == IToken.t_class ? ICPPASTSimpleTypeTemplateParameter.st_class
: ICPPASTSimpleTypeTemplateParameter.st_typename); : ICPPASTSimpleTypeTemplateParameter.st_typename);
lastOffset = consume().getEndOffset(); boolean parameterPack= false;
IASTName identifierName = null; IASTName identifierName = null;
IASTTypeId typeId = null; IASTTypeId defaultValue = null;
int endOffset = consume().getEndOffset();
if (LT(1) == IToken.tELLIPSIS) {
parameterPack= true;
endOffset= consume().getOffset();
}
if (LT(1) == IToken.tIDENTIFIER) { // optional identifier if (LT(1) == IToken.tIDENTIFIER) { // optional identifier
identifierName = identifier(); identifierName = identifier();
lastOffset = calculateEndOffset(identifierName); endOffset = calculateEndOffset(identifierName);
if (LT(1) == IToken.tASSIGN) { // optional = type-id if (LT(1) == IToken.tASSIGN) { // optional = type-id
consume(); if (parameterPack)
typeId = typeId(DeclarationOptions.TYPEID); // type-id
if (typeId == null)
throw backtrack; throw backtrack;
lastOffset = calculateEndOffset(typeId); consume();
defaultValue = typeId(DeclarationOptions.TYPEID); // type-id
if (defaultValue == null)
throw backtrack;
endOffset = calculateEndOffset(defaultValue);
} }
} else { } else {
identifierName = nodeFactory.newName(); identifierName = nodeFactory.newName();
} }
ICPPASTSimpleTypeTemplateParameter parm = nodeFactory.newSimpleTypeTemplateParameter(type, identifierName, typeId); ICPPASTSimpleTypeTemplateParameter tpar = nodeFactory.newSimpleTypeTemplateParameter(type, identifierName, defaultValue);
((ASTNode) parm).setOffsetAndLength(startingToken.getOffset(), lastOffset - startingToken.getOffset()); tpar.setIsParameterPack(parameterPack);
returnValue.add(parm); setRange(tpar, offset, endOffset);
returnValue.add(tpar);
} else if (lt1 == IToken.t_template) { } else if (lt1 == IToken.t_template) {
IToken firstToken = consume(); boolean parameterPack= false;
consume(IToken.tLT);
List<ICPPASTTemplateParameter> subResult = templateParameterList();
consume(IToken.tGT, IToken.tGT_in_SHIFTR);
int last = consume(IToken.t_class).getEndOffset();
IASTName identifierName = null; IASTName identifierName = null;
IASTExpression optionalExpression = null; IASTExpression defaultValue = null;
consume();
consume(IToken.tLT);
List<ICPPASTTemplateParameter> tparList = templateParameterList();
consume(IToken.tGT, IToken.tGT_in_SHIFTR);
int endOffset = consume(IToken.t_class).getEndOffset();
if (LT(1) == IToken.tELLIPSIS) {
parameterPack= true;
endOffset= consume().getOffset();
}
if (LT(1) == IToken.tIDENTIFIER) { // optional identifier if (LT(1) == IToken.tIDENTIFIER) { // optional identifier
identifierName = identifier(); identifierName = identifier();
last = calculateEndOffset(identifierName); endOffset = calculateEndOffset(identifierName);
if (LT(1) == IToken.tASSIGN) { // optional = type-id if (LT(1) == IToken.tASSIGN) { // optional = type-id
if (parameterPack)
throw backtrack;
consume(); consume();
optionalExpression = primaryExpression(CastExprCtx.eNotBExpr); defaultValue = primaryExpression(CastExprCtx.eNotBExpr);
last = calculateEndOffset(optionalExpression); endOffset = calculateEndOffset(defaultValue);
} }
} else } else {
identifierName = nodeFactory.newName(); identifierName = nodeFactory.newName();
ICPPASTTemplatedTypeTemplateParameter parm = nodeFactory.newTemplatedTypeTemplateParameter(identifierName, optionalExpression);
((ASTNode) parm).setOffsetAndLength(firstToken.getOffset(), last - firstToken.getOffset());
for (int i = 0; i < subResult.size(); ++i) {
ICPPASTTemplateParameter p = subResult.get(i);
parm.addTemplateParamter(p);
} }
returnValue.add(parm);
ICPPASTTemplatedTypeTemplateParameter tpar = nodeFactory.newTemplatedTypeTemplateParameter(identifierName, defaultValue);
tpar.setIsParameterPack(parameterPack);
setRange(tpar, offset, endOffset);
for (int i = 0; i < tparList.size(); ++i) {
ICPPASTTemplateParameter p = tparList.get(i);
tpar.addTemplateParamter(p);
}
returnValue.add(tpar);
} else if (lt1 == IToken.tCOMMA) { } else if (lt1 == IToken.tCOMMA) {
consume(); consume();
continue; continue;
@ -2045,6 +2124,10 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} }
ICPPASTConstructorChainInitializer ctorInitializer = nodeFactory.newConstructorChainInitializer(name, expressionList); ICPPASTConstructorChainInitializer ctorInitializer = nodeFactory.newConstructorChainInitializer(name, expressionList);
if (LT(1) == IToken.tELLIPSIS) {
ctorInitializer.setIsPackExpansion(true);
endOffset= consume().getEndOffset();
}
setRange(ctorInitializer, offset, endOffset); setRange(ctorInitializer, offset, endOffset);
fdef.addMemberInitializer(ctorInitializer); fdef.addMemberInitializer(ctorInitializer);
@ -2753,36 +2836,10 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} }
protected IASTInitializer initializerClause(boolean inAggregateInitializer) throws EndOfFileException, protected ICPPASTInitializer initializerClause(boolean inAggregateInitializer) throws EndOfFileException,
BacktrackException { BacktrackException {
if (LT(1) == IToken.tLBRACE) { if (LT(1) == IToken.tLBRACE) {
int startingOffset = consume().getOffset(); return initializerList();
IASTInitializerList result = nodeFactory.newInitializerList();
((ASTNode) result).setOffset(startingOffset);
if (LT(1) == (IToken.tRBRACE)) {
int endOffset = consume().getEndOffset();
setRange(result, startingOffset, endOffset);
return result;
}
// otherwise it is a list of initializer clauses
for (;;) {
if (LT(1) == IToken.tRBRACE)
break;
// clause may be null, add to initializer anyways, such that the
// actual size can be computed.
IASTInitializer clause = initializerClause(true);
result.addInitializer(clause);
if (LT(1) == IToken.tRBRACE || LT(1) == IToken.tEOC)
break;
consume(IToken.tCOMMA);
}
int endOffset = consume().getEndOffset(); // tRBRACE
setRange(result, startingOffset, endOffset);
return result;
} }
// no brace, so try an assignment expression // no brace, so try an assignment expression
@ -2793,14 +2850,38 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
return null; return null;
} }
IASTInitializerExpression result = nodeFactory.newInitializerExpression(assignmentExpression); ICPPASTInitializerExpression result = nodeFactory.newInitializerExpression(assignmentExpression);
setRange(result, assignmentExpression); setRange(result, assignmentExpression);
return result; return result;
} }
private ICPPASTInitializerList initializerList() throws EndOfFileException, BacktrackException {
int startingOffset = consume(IToken.tLBRACE).getOffset();
ICPPASTInitializerList result = nodeFactory.newInitializerList();
// List of initializer clauses
while (LT(1) != IToken.tRBRACE && LT(1) != IToken.tEOC) {
// Clause may be null, add to initializer anyways, such that the
// actual size can be computed.
ICPPASTInitializer clause = initializerClause(true);
if (LT(1) == IToken.tELLIPSIS) {
clause.setIsPackExpansion(true);
adjustEndOffset(clause, consume().getEndOffset());
}
result.addInitializer(clause);
if (LT(1) == IToken.tRBRACE || LT(1) == IToken.tEOC)
break;
consume(IToken.tCOMMA); // Allow for trailing commas
}
int endOffset = consume().getEndOffset(); // tRBRACE
setRange(result, startingOffset, endOffset);
return result;
}
@Override @Override
protected IASTTypeId typeId(DeclarationOptions option) throws EndOfFileException { protected ICPPASTTypeId typeId(DeclarationOptions option) throws EndOfFileException {
if (!canBeTypeSpecifier()) { if (!canBeTypeSpecifier()) {
return null; return null;
} }
@ -2818,7 +2899,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} catch (BacktrackException bt) { } catch (BacktrackException bt) {
return null; return null;
} }
IASTTypeId result = nodeFactory.newTypeId(declSpecifier, declarator); ICPPASTTypeId result = nodeFactory.newTypeId(declSpecifier, declarator);
setRange(result, offset, figureEndOffset(declSpecifier, declarator)); setRange(result, offset, figureEndOffset(declSpecifier, declarator));
return result; return result;
@ -2845,9 +2926,8 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
final int startingOffset = LA(1).getOffset(); final int startingOffset = LA(1).getOffset();
int endOffset = startingOffset; int endOffset = startingOffset;
List<IASTPointerOperator> pointerOps = new ArrayList<IASTPointerOperator>(DEFAULT_POINTEROPS_LIST_SIZE); List<? extends IASTPointerOperator> pointerOps = consumePointerOperators();
consumePointerOperators(pointerOps); if (pointerOps != null) {
if (!pointerOps.isEmpty()) {
endOffset = calculateEndOffset(pointerOps.get(pointerOps.size() - 1)); endOffset = calculateEndOffset(pointerOps.get(pointerOps.size() - 1));
} }
@ -2855,6 +2935,11 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
__attribute_decl_seq(supportAttributeSpecifiers, supportDeclspecSpecifiers); __attribute_decl_seq(supportAttributeSpecifiers, supportDeclspecSpecifiers);
// Look for identifier or nested declarator // Look for identifier or nested declarator
boolean hasEllipsis= false;
if (option.fAllowParameterPacks && LT(1) == IToken.tELLIPSIS) {
consume();
hasEllipsis= true;
}
final int lt1= LT(1); final int lt1= LT(1);
switch (lt1) { switch (lt1) {
case IToken.tBITCOMPLEMENT: case IToken.tBITCOMPLEMENT:
@ -2867,7 +2952,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
final IASTName declaratorName= qualifiedName(CastExprCtx.eNotBExpr); final IASTName declaratorName= qualifiedName(CastExprCtx.eNotBExpr);
endOffset= calculateEndOffset(declaratorName); endOffset= calculateEndOffset(declaratorName);
return declarator(pointerOps, declaratorName, null, startingOffset, endOffset, strategy, option); return declarator(pointerOps, hasEllipsis, declaratorName, null, startingOffset, endOffset, strategy, option);
} }
if (lt1 == IToken.tLPAREN) { if (lt1 == IToken.tLPAREN) {
@ -2877,8 +2962,8 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
if (option.fAllowAbstract && option.fAllowFunctions) { if (option.fAllowAbstract && option.fAllowFunctions) {
final IToken mark= mark(); final IToken mark= mark();
try { try {
cand1= declarator(pointerOps, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option); cand1= declarator(pointerOps, hasEllipsis, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option);
if (option.fRequireAbstract || !option.fAllowNested) if (option.fRequireAbstract || !option.fAllowNested || hasEllipsis)
return cand1; return cand1;
cand1End= LA(1); cand1End= LA(1);
@ -2888,9 +2973,9 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} }
// type-ids for new or operator-id: // type-ids for new or operator-id:
if (!option.fAllowNested) { if (!option.fAllowNested || hasEllipsis) {
if (option.fAllowAbstract) { if (option.fAllowAbstract) {
return declarator(pointerOps, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option); return declarator(pointerOps, hasEllipsis, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option);
} }
throwBacktrack(LA(1)); throwBacktrack(LA(1));
} }
@ -2903,7 +2988,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
final IASTDeclarator nested= declarator(DtorStrategy.PREFER_FUNCTION, option); final IASTDeclarator nested= declarator(DtorStrategy.PREFER_FUNCTION, option);
endOffset= consume(IToken.tRPAREN).getEndOffset(); endOffset= consume(IToken.tRPAREN).getEndOffset();
final IASTDeclarator cand2= declarator(pointerOps, null, nested, startingOffset, endOffset, strategy, option); final IASTDeclarator cand2= declarator(pointerOps, hasEllipsis, nodeFactory.newName(), nested, startingOffset, endOffset, strategy, option);
if (cand1 == null || cand1End == null) if (cand1 == null || cand1End == null)
return cand2; return cand2;
final IToken cand2End= LA(1); final IToken cand2End= LA(1);
@ -2930,7 +3015,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
if (!option.fAllowBitField || LT(1) != IToken.tCOLON) if (!option.fAllowBitField || LT(1) != IToken.tCOLON)
throwBacktrack(LA(1)); throwBacktrack(LA(1));
} }
return declarator(pointerOps, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option); return declarator(pointerOps, hasEllipsis, nodeFactory.newName(), null, startingOffset, endOffset, strategy, option);
} }
/** /**
@ -2940,9 +3025,8 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
* @throws BacktrackException * @throws BacktrackException
* request a backtrack * request a backtrack
*/ */
private void consumePointerOperators(List<IASTPointerOperator> collection) private List<? extends IASTPointerOperator> consumePointerOperators() throws EndOfFileException, BacktrackException {
throws EndOfFileException, BacktrackException { List<IASTPointerOperator> result= null;
for (;;) { for (;;) {
// __attribute__ in-between pointers // __attribute__ in-between pointers
__attribute_decl_seq(supportAttributeSpecifiers, false); __attribute_decl_seq(supportAttributeSpecifiers, false);
@ -2956,8 +3040,12 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
endToken= consume(); endToken= consume();
} }
ICPPASTReferenceOperator refOp = nodeFactory.newReferenceOperator(lt1 == IToken.tAND); ICPPASTReferenceOperator refOp = nodeFactory.newReferenceOperator(lt1 == IToken.tAND);
collection.add(setRange(refOp, offset, endToken.getEndOffset())); setRange(refOp, offset, endToken.getEndOffset());
return; if (result != null) {
result.add(refOp);
return result;
}
return Collections.singletonList(refOp);
} }
IToken mark = mark(); IToken mark = mark();
@ -2983,16 +3071,16 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
name= qualifiedName(CastExprCtx.eNotBExpr); name= qualifiedName(CastExprCtx.eNotBExpr);
if (name.getLookupKey().length != 0) { if (name.getLookupKey().length != 0) {
backup(mark); backup(mark);
return; return result;
} }
} catch (BacktrackException bt) { } catch (BacktrackException bt) {
backup(mark); backup(mark);
return; return result;
} }
} }
if (LTcatchEOF(1) != IToken.tSTAR) { if (LTcatchEOF(1) != IToken.tSTAR) {
backup(mark); backup(mark);
return; return result;
} }
int endOffset= consume().getEndOffset(); int endOffset= consume().getEndOffset();
@ -3039,28 +3127,31 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
pointer.setConst(isConst); pointer.setConst(isConst);
pointer.setVolatile(isVolatile); pointer.setVolatile(isVolatile);
setRange(pointer, startOffset, endOffset); setRange(pointer, startOffset, endOffset);
collection.add(pointer); if (result == null) {
result= new ArrayList<IASTPointerOperator>(4);
}
result.add(pointer);
} }
} }
private IASTDeclarator declarator(List<IASTPointerOperator> pointerOps, private IASTDeclarator declarator(List<? extends IASTPointerOperator> pointerOps, boolean hasEllipsis,
IASTName declaratorName, IASTDeclarator nestedDeclarator, int startingOffset, int endOffset, IASTName declaratorName, IASTDeclarator nestedDeclarator, int startingOffset, int endOffset,
DtorStrategy strategy, DeclarationOptions option) DtorStrategy strategy, DeclarationOptions option)
throws EndOfFileException, BacktrackException { throws EndOfFileException, BacktrackException {
IASTDeclarator result= null; ICPPASTDeclarator result= null;
loop: while(true) { loop: while(true) {
final int lt1= LTcatchEOF(1); final int lt1= LTcatchEOF(1);
switch (lt1) { switch (lt1) {
case IToken.tLPAREN: case IToken.tLPAREN:
if (option.fAllowFunctions && strategy == DtorStrategy.PREFER_FUNCTION) { if (option.fAllowFunctions && strategy == DtorStrategy.PREFER_FUNCTION) {
result= functionDeclarator(); result= functionDeclarator();
setDeclaratorID(result, declaratorName, nestedDeclarator); setDeclaratorID(result, hasEllipsis, declaratorName, nestedDeclarator);
} }
break loop; break loop;
case IToken.tLBRACKET: case IToken.tLBRACKET:
result= arrayDeclarator(option); result= arrayDeclarator(option);
setDeclaratorID(result, declaratorName, nestedDeclarator); setDeclaratorID(result, hasEllipsis, declaratorName, nestedDeclarator);
break loop; break loop;
case IToken.tCOLON: case IToken.tCOLON:
@ -3068,7 +3159,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
break loop; // no backtrack because typeid can be followed by colon break loop; // no backtrack because typeid can be followed by colon
result= bitFieldDeclarator(); result= bitFieldDeclarator();
setDeclaratorID(result, declaratorName, nestedDeclarator); setDeclaratorID(result, hasEllipsis, declaratorName, nestedDeclarator);
break loop; break loop;
case IGCCToken.t__attribute__: // if __attribute__ is after a declarator case IGCCToken.t__attribute__: // if __attribute__ is after a declarator
@ -3089,7 +3180,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
if (result == null) { if (result == null) {
result= nodeFactory.newDeclarator(null); result= nodeFactory.newDeclarator(null);
setDeclaratorID(result, declaratorName, nestedDeclarator); setDeclaratorID(result, hasEllipsis, declaratorName, nestedDeclarator);
} else { } else {
endOffset= calculateEndOffset(result); endOffset= calculateEndOffset(result);
} }
@ -3101,33 +3192,36 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
__attribute_decl_seq(supportAttributeSpecifiers, supportDeclspecSpecifiers); __attribute_decl_seq(supportAttributeSpecifiers, supportDeclspecSpecifiers);
} }
if (pointerOps != null) {
for (IASTPointerOperator po : pointerOps) { for (IASTPointerOperator po : pointerOps) {
result.addPointerOperator(po); result.addPointerOperator(po);
} }
}
((ASTNode) result).setOffsetAndLength(startingOffset, endOffset - startingOffset); ((ASTNode) result).setOffsetAndLength(startingOffset, endOffset - startingOffset);
return result; return result;
} }
private void setDeclaratorID(IASTDeclarator declarator, IASTName declaratorName, IASTDeclarator nestedDeclarator) { private void setDeclaratorID(ICPPASTDeclarator declarator, boolean hasEllipsis, IASTName declaratorName, IASTDeclarator nestedDeclarator) {
if (nestedDeclarator != null) { if (nestedDeclarator != null) {
declarator.setNestedDeclarator(nestedDeclarator); declarator.setNestedDeclarator(nestedDeclarator);
declarator.setName(nodeFactory.newName()); declarator.setName(nodeFactory.newName());
} else { } else {
declarator.setName(declaratorName); declarator.setName(declaratorName);
} }
declarator.setDeclaresParameterPack(hasEllipsis);
} }
/** /**
* Parse a function declarator starting with the left parenthesis. * Parse a function declarator starting with the left parenthesis.
*/ */
private IASTDeclarator functionDeclarator() throws EndOfFileException, BacktrackException { private ICPPASTDeclarator functionDeclarator() throws EndOfFileException, BacktrackException {
IToken last = consume(IToken.tLPAREN); IToken last = consume(IToken.tLPAREN);
int startOffset= last.getOffset(); int startOffset= last.getOffset();
boolean seenParameter= false;
int endOffset= last.getEndOffset(); int endOffset= last.getEndOffset();
final ICPPASTFunctionDeclarator fc = nodeFactory.newFunctionDeclarator(null); final ICPPASTFunctionDeclarator fc = nodeFactory.newFunctionDeclarator(null);
ICPPASTParameterDeclaration pd= null;
paramLoop: while(true) { paramLoop: while(true) {
switch (LT(1)) { switch (LT(1)) {
case IToken.tRPAREN: case IToken.tRPAREN:
@ -3135,24 +3229,36 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
endOffset= consume().getEndOffset(); endOffset= consume().getEndOffset();
break paramLoop; break paramLoop;
case IToken.tELLIPSIS: case IToken.tELLIPSIS:
endOffset= consume().getEndOffset(); consume();
endOffset= consume(IToken.tRPAREN).getEndOffset();
fc.setVarArgs(true); fc.setVarArgs(true);
break; break paramLoop;
case IToken.tCOMMA: case IToken.tCOMMA:
if (pd == null)
throwBacktrack(LA(1));
endOffset= consume().getEndOffset(); endOffset= consume().getEndOffset();
seenParameter = false; pd= null;
break; break;
default: default:
if (seenParameter) if (pd != null)
throwBacktrack(startOffset, endOffset - startOffset); throwBacktrack(startOffset, endOffset - startOffset);
IASTParameterDeclaration pd = parameterDeclaration(); pd = parameterDeclaration();
fc.addParameterDeclaration(pd); fc.addParameterDeclaration(pd);
endOffset = calculateEndOffset(pd); endOffset = calculateEndOffset(pd);
seenParameter = true;
break; break;
} }
} }
// Handle ambiguity between parameter pack and varargs.
if (pd != null) {
ICPPASTDeclarator dtor = pd.getDeclarator();
if (!(dtor instanceof IASTAmbiguousDeclarator)) {
if (dtor.declaresParameterPack() && dtor.getNestedDeclarator() == null
&& dtor.getInitializer() == null && dtor.getName().getSimpleID().length == 0) {
((IASTAmbiguityParent) fc).replace(pd, new CPPASTAmbiguousParameterDeclaration(pd));
}
}
}
// Consume any number of __attribute__ tokens after the parameters // Consume any number of __attribute__ tokens after the parameters
__attribute_decl_seq(supportAttributeSpecifiers, false); __attribute_decl_seq(supportAttributeSpecifiers, false);
@ -3190,8 +3296,12 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
break; break;
default: default:
int thoffset = LA(1).getOffset(); int thoffset = LA(1).getOffset();
IASTTypeId typeId = typeId(DeclarationOptions.TYPEID); ICPPASTTypeId typeId = typeId(DeclarationOptions.TYPEID);
if (typeId != null) { if (typeId != null) {
if (LT(1) == IToken.tELLIPSIS) {
typeId.setIsPackExpansion(true);
adjustEndOffset(typeId, consume().getEndOffset());
}
fc.addExceptionSpecificationTypeId(typeId); fc.addExceptionSpecificationTypeId(typeId);
} else { } else {
int thendoffset = LA(1).getOffset(); int thendoffset = LA(1).getOffset();
@ -3218,15 +3328,15 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
/** /**
* Parse an array declarator starting at the square bracket. * Parse an array declarator starting at the square bracket.
*/ */
private IASTArrayDeclarator arrayDeclarator(DeclarationOptions option) throws EndOfFileException, BacktrackException { private ICPPASTArrayDeclarator arrayDeclarator(DeclarationOptions option) throws EndOfFileException, BacktrackException {
ArrayList<IASTArrayModifier> arrayMods = new ArrayList<IASTArrayModifier>(DEFAULT_POINTEROPS_LIST_SIZE); ArrayList<IASTArrayModifier> arrayMods = new ArrayList<IASTArrayModifier>(4);
int start= LA(1).getOffset(); int start= LA(1).getOffset();
consumeArrayModifiers(option, arrayMods); consumeArrayModifiers(option, arrayMods);
if (arrayMods.isEmpty()) if (arrayMods.isEmpty())
throwBacktrack(LA(1)); throwBacktrack(LA(1));
final int endOffset = calculateEndOffset(arrayMods.get(arrayMods.size() - 1)); final int endOffset = calculateEndOffset(arrayMods.get(arrayMods.size() - 1));
final IASTArrayDeclarator d = nodeFactory.newArrayDeclarator(null); final ICPPASTArrayDeclarator d = nodeFactory.newArrayDeclarator(null);
for (IASTArrayModifier m : arrayMods) { for (IASTArrayModifier m : arrayMods) {
d.addArrayModifier(m); d.addArrayModifier(m);
} }
@ -3239,13 +3349,13 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
/** /**
* Parses for a bit field declarator starting with the colon * Parses for a bit field declarator starting with the colon
*/ */
private IASTFieldDeclarator bitFieldDeclarator() throws EndOfFileException, BacktrackException { private ICPPASTFieldDeclarator bitFieldDeclarator() throws EndOfFileException, BacktrackException {
int start= consume(IToken.tCOLON).getOffset(); int start= consume(IToken.tCOLON).getOffset();
final IASTExpression bitField = constantExpression(); final IASTExpression bitField = constantExpression();
final int endOffset = calculateEndOffset(bitField); final int endOffset = calculateEndOffset(bitField);
IASTFieldDeclarator d = nodeFactory.newFieldDeclarator(null, bitField); ICPPASTFieldDeclarator d = nodeFactory.newFieldDeclarator(null, bitField);
((ASTNode) d).setOffsetAndLength(start, endOffset-start); ((ASTNode) d).setOffsetAndLength(start, endOffset-start);
return d; return d;
} }
@ -3298,7 +3408,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
// base clause // base clause
if (LT(1) == IToken.tCOLON) { if (LT(1) == IToken.tCOLON) {
baseSpecifier(astClassSpecifier); baseClause(astClassSpecifier);
// content assist within the base-clause // content assist within the base-clause
if (LT(1) == IToken.tEOC) { if (LT(1) == IToken.tEOC) {
return astClassSpecifier; return astClassSpecifier;
@ -3335,76 +3445,74 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
} }
/** /**
* Parse the subclass-baseclauses for a class specification. baseclause: : * Parse a base clause for a class specification.
* basespecifierlist basespecifierlist: basespecifier basespecifierlist, * base-clause:
* basespecifier basespecifier: ::? nestednamespecifier? classname virtual * : base-specifier-list
* accessspecifier? ::? nestednamespecifier? classname accessspecifier * base-specifier-list:
* virtual? ::? nestednamespecifier? classname accessspecifier: private | * base-specifier
* protected | public * base-specifier-list, base-specifier
*
* @throws BacktrackException
*/ */
protected void baseSpecifier(ICPPASTCompositeTypeSpecifier astClassSpec) throws EndOfFileException, BacktrackException { private void baseClause(ICPPASTCompositeTypeSpecifier astClassSpec) throws EndOfFileException, BacktrackException {
int endOffset= consume().getEndOffset(); // tCOLON consume(IToken.tCOLON);
int startOffset= LA(1).getOffset(); for (;;) {
ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier baseSpec = baseSpecifier();
astClassSpec.addBaseSpecifier(baseSpec);
if (LT(1) == IToken.tELLIPSIS) {
baseSpec.setIsPackExpansion(true);
adjustEndOffset(baseSpec, consume().getEndOffset());
}
if (LT(1) != IToken.tCOMMA) {
return;
}
consume();
}
}
/**
* base-specifier:
* ::? nested-name-specifier? class-name
* virtual access-specifier? ::? nested-name-specifier? class-name
* access-specifier virtual? ::? nested-name-specifier? class-name
*
* access-specifier: private | protected | public
* @return
*/
private ICPPASTBaseSpecifier baseSpecifier() throws EndOfFileException, BacktrackException {
int startOffset= LA(1).getOffset();
boolean isVirtual = false; boolean isVirtual = false;
int visibility = 0; int visibility = 0;
IASTName name = null; IASTName name = null;
baseSpecifierLoop: for (;;) { loop: for (;;) {
switch (LT(1)) { switch (LT(1)) {
case IToken.t_virtual: case IToken.t_virtual:
isVirtual = true; isVirtual = true;
endOffset= consume().getEndOffset(); consume();
break; break;
case IToken.t_public: case IToken.t_public:
visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_public; visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_public;
endOffset= consume().getEndOffset(); consume();
break; break;
case IToken.t_protected: case IToken.t_protected:
visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_protected; visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_protected;
endOffset= consume().getEndOffset(); consume();
break; break;
case IToken.t_private: case IToken.t_private:
visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_private; visibility = ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier.v_private;
endOffset= consume().getEndOffset();
break;
case IToken.tCOLONCOLON:
case IToken.tIDENTIFIER:
case IToken.tCOMPLETION:
// to get templates right we need to use the class as the scope
name = qualifiedName(CastExprCtx.eNotBExpr);
endOffset= calculateEndOffset(name);
break;
case IToken.tCOMMA:
if (name == null)
name = nodeFactory.newName();
consume(); consume();
ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier baseSpec = nodeFactory.newBaseSpecifier(name, visibility, isVirtual); break;
setRange(baseSpec, startOffset, endOffset);
astClassSpec.addBaseSpecifier(baseSpec);
isVirtual = false;
visibility = 0;
name = null;
startOffset= endOffset= LA(1).getOffset();
continue baseSpecifierLoop;
case IToken.tLBRACE:
case IToken.tEOC:
if (name == null)
name = nodeFactory.newName();
baseSpec = nodeFactory.newBaseSpecifier(name, visibility, isVirtual);
setRange(baseSpec, startOffset, endOffset);
astClassSpec.addBaseSpecifier(baseSpec);
break baseSpecifierLoop;
default: default:
break baseSpecifierLoop; break loop;
} }
} }
name = qualifiedName(CastExprCtx.eNotBExpr);
ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier baseSpec = nodeFactory.newBaseSpecifier(name, visibility, isVirtual);
setRange(baseSpec, startOffset, calculateEndOffset(name));
return baseSpec;
} }
protected void catchHandlerSequence(List<ICPPASTCatchHandler> collection) throws EndOfFileException, BacktrackException { protected void catchHandlerSequence(List<ICPPASTCatchHandler> collection) throws EndOfFileException, BacktrackException {
if (LT(1) == IToken.tEOC) if (LT(1) == IToken.tEOC)
return; return;

View file

@ -65,14 +65,12 @@ import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.IASTTypeIdExpression; import org.eclipse.cdt.core.dom.ast.IASTTypeIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTTypeIdInitializerExpression; import org.eclipse.cdt.core.dom.ast.IASTTypeIdInitializerExpression;
import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression; import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.ICompositeType; import org.eclipse.cdt.core.dom.ast.ICompositeType;
import org.eclipse.cdt.core.dom.ast.IEnumeration; import org.eclipse.cdt.core.dom.ast.IEnumeration;
import org.eclipse.cdt.core.dom.ast.IEnumerator; import org.eclipse.cdt.core.dom.ast.IEnumerator;
import org.eclipse.cdt.core.dom.ast.IFunction; import org.eclipse.cdt.core.dom.ast.IFunction;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IParameter;
import org.eclipse.cdt.core.dom.ast.IPointerType; import org.eclipse.cdt.core.dom.ast.IPointerType;
import org.eclipse.cdt.core.dom.ast.IProblemBinding; import org.eclipse.cdt.core.dom.ast.IProblemBinding;
import org.eclipse.cdt.core.dom.ast.IQualifierType; import org.eclipse.cdt.core.dom.ast.IQualifierType;
@ -87,6 +85,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName; 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.ICPPASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeleteExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTForStatement;
@ -106,6 +105,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUnaryExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTWhileStatement; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTWhileStatement;
@ -446,6 +446,9 @@ public class CPPSemantics {
IASTNode parent= name.getParent().getParent(); IASTNode parent= name.getParent().getParent();
if (parent instanceof ICPPASTTemplatedTypeTemplateParameter) { if (parent instanceof ICPPASTTemplatedTypeTemplateParameter) {
// default for template template parameter is an id-expression, which is a type. // default for template template parameter is an id-expression, which is a type.
} else if (parent instanceof ICPPASTUnaryExpression
&& ((ICPPASTUnaryExpression) parent).getOperator() == IASTUnaryExpression.op_sizeofParameterPack) {
// argument of sizeof... can be a type
} else if (data.considerConstructors && } else if (data.considerConstructors &&
(binding instanceof ICPPUnknownType || binding instanceof ITypedef || binding instanceof IEnumeration)) { (binding instanceof ICPPUnknownType || binding instanceof ITypedef || binding instanceof IEnumeration)) {
// constructor or simple-type constructor // constructor or simple-type constructor
@ -959,6 +962,7 @@ public class CPPSemantics {
if (expression instanceof IASTUnaryExpression) { if (expression instanceof IASTUnaryExpression) {
switch (((IASTUnaryExpression) expression).getOperator()) { switch (((IASTUnaryExpression) expression).getOperator()) {
case IASTUnaryExpression.op_sizeof: case IASTUnaryExpression.op_sizeof:
case IASTUnaryExpression.op_sizeofParameterPack:
case IASTUnaryExpression.op_typeid: case IASTUnaryExpression.op_typeid:
case IASTUnaryExpression.op_throw: case IASTUnaryExpression.op_throw:
return PROCESS_SKIP; return PROCESS_SKIP;
@ -1949,25 +1953,23 @@ public class CPPSemantics {
if (def && argumentCount == 1) { if (def && argumentCount == 1) {
// check for parameter of type void // check for parameter of type void
final IType[] argTypes = data.getFunctionArgumentTypes(); final IType[] argTypes = data.getFunctionArgumentTypes();
if (argTypes.length == 1) { if (argTypes.length == 1 && SemanticUtil.isVoidType(argTypes[0])) {
IType t= getNestedType(argTypes[0], TDEF);
if (t instanceof IBasicType && ((IBasicType)t).getKind() == Kind.eVoid) {
argumentCount= 0; argumentCount= 0;
} }
} }
}
// Trim the list down to the set of viable functions // Trim the list down to the set of viable functions
IFunction function = null; ICPPFunction function = null;
int size = functions.length; int size = functions.length;
for (int i = 0; i < size; i++) { for (int i = 0; i < size; i++) {
function = (IFunction) functions[i]; if (functions[i] instanceof IProblemBinding) {
if (function == null)
continue;
if (function instanceof IProblemBinding) {
functions[i]= null; functions[i]= null;
continue; continue;
} }
function = (ICPPFunction) functions[i];
if (function == null)
continue;
if (function instanceof ICPPUnknownBinding) { if (function instanceof ICPPUnknownBinding) {
if (def) { if (def) {
functions[i]= null; functions[i]= null;
@ -1979,47 +1981,31 @@ public class CPPSemantics {
// as long as possible. // as long as possible.
final IType[] parameterTypes = function.getType().getParameterTypes(); final IType[] parameterTypes = function.getType().getParameterTypes();
int numPars = parameterTypes.length; int numPars = parameterTypes.length;
if (numPars == 1 && SemanticUtil.isVoidType(parameterTypes[0]))
numPars= 0;
int numArgs = argumentCount; int numArgs = argumentCount;
if (function instanceof ICPPMethod && data.firstArgIsImpliedMethodArg) if (function instanceof ICPPMethod && data.firstArgIsImpliedMethodArg)
numArgs--; numArgs--;
if (numArgs < 2 && numPars == 1) {
// check for void
IType t = getNestedType(parameterTypes[0], TDEF);
if (t instanceof IBasicType && ((IBasicType)t).getKind() == Kind.eVoid)
numPars= 0;
}
if (def) { if (def) {
if (numPars != numArgs || !isMatchingFunctionDeclaration(function, data)) { if (numPars != numArgs || !isMatchingFunctionDeclaration(function, data)) {
functions[i] = null; functions[i] = null;
} }
} else { } else {
// more arguments than parameters --> need ellipses // more arguments than parameters --> need ellipsis
if (numArgs > numPars) { if (numArgs > numPars) {
if (!function.takesVarArgs()) { if (!function.takesVarArgs() && !function.hasParameterPack()) {
functions[i] = null; functions[i] = null;
} }
} else if (numArgs < numPars) { } else if (numArgs < function.getRequiredArgumentCount()) {
// fewer arguments than parameters --> need default values // fewer arguments than required
IParameter[] params = function.getParameters();
if (params.length < numPars) {
functions[i]= null; functions[i]= null;
} else {
for (int j = numArgs; j < numPars; j++) {
final ICPPParameter param = (ICPPParameter) params[j];
if (param == null || !param.hasDefaultValue()) {
functions[i] = null;
break;
} }
} }
} }
} }
} static private boolean isMatchingFunctionDeclaration(ICPPFunction candidate, LookupData data) {
}
}
static private boolean isMatchingFunctionDeclaration(IFunction candidate, LookupData data) {
IASTNode node = data.astName.getParent(); IASTNode node = data.astName.getParent();
while (node instanceof IASTName) while (node instanceof IASTName)
node = node.getParent(); node = node.getParent();
@ -3039,8 +3025,9 @@ public class CPPSemantics {
return set.keyArray(IBinding.class); return set.keyArray(IBinding.class);
} }
public static boolean isSameFunction(IFunction function, IASTDeclarator declarator) { public static boolean isSameFunction(ICPPFunction function, IASTDeclarator declarator) {
IASTName name = ASTQueries.findInnermostDeclarator(declarator).getName(); final ICPPASTDeclarator innerDtor = (ICPPASTDeclarator) ASTQueries.findInnermostDeclarator(declarator);
IASTName name = innerDtor.getName();
ICPPASTTemplateDeclaration templateDecl = CPPTemplates.getTemplateDeclaration(name); ICPPASTTemplateDeclaration templateDecl = CPPTemplates.getTemplateDeclaration(name);
if (templateDecl != null) { if (templateDecl != null) {
if (templateDecl instanceof ICPPASTTemplateSpecialization) { if (templateDecl instanceof ICPPASTTemplateSpecialization) {

View file

@ -74,6 +74,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunction;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionTemplate; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionTemplate;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod; import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPScope; import org.eclipse.cdt.core.dom.ast.cpp.ICPPScope;
@ -119,6 +120,7 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPFunctionType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodInstance; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodInstance;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodSpecialization; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodSpecialization;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodTemplateSpecialization; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodTemplateSpecialization;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPReferenceType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPReferenceType;
@ -400,8 +402,13 @@ public class CPPTemplates {
for (int i = 0; i < templateParameters.length; i++) { for (int i = 0; i < templateParameters.length; i++) {
final ICPPTemplateParameter tp = templateParameters[i]; final ICPPTemplateParameter tp = templateParameters[i];
if (tp instanceof IType) { if (tp instanceof IType) {
args[i] = new CPPTemplateArgument((IType) tp); IType t= (IType) tp;
if (tp.isParameterPack()) {
t= new CPPParameterPackType(t);
}
args[i] = new CPPTemplateArgument(t);
} else if (tp instanceof ICPPTemplateNonTypeParameter) { } else if (tp instanceof ICPPTemplateNonTypeParameter) {
// Non-type template parameter pack already has type 'ICPPParameterPackType'
final ICPPTemplateNonTypeParameter nttp = (ICPPTemplateNonTypeParameter) tp; final ICPPTemplateNonTypeParameter nttp = (ICPPTemplateNonTypeParameter) tp;
args[i] = new CPPTemplateArgument(Value.create(nttp), nttp.getType()); args[i] = new CPPTemplateArgument(Value.create(nttp), nttp.getType());
} else { } else {
@ -490,15 +497,15 @@ public class CPPTemplates {
return (binding instanceof ICPPTemplateDefinition) ? (ICPPTemplateDefinition) binding : null; return (binding instanceof ICPPTemplateDefinition) ? (ICPPTemplateDefinition) binding : null;
} }
public static IBinding createBinding(ICPPASTTemplateParameter templateParameter) { public static IBinding createBinding(ICPPASTTemplateParameter tp) {
if (templateParameter instanceof ICPPASTSimpleTypeTemplateParameter) { if (tp instanceof ICPPASTSimpleTypeTemplateParameter) {
return new CPPTemplateTypeParameter(((ICPPASTSimpleTypeTemplateParameter) templateParameter).getName()); return new CPPTemplateTypeParameter(((ICPPASTSimpleTypeTemplateParameter) tp).getName(), tp.isParameterPack());
} }
if (templateParameter instanceof ICPPASTTemplatedTypeTemplateParameter) { if (tp instanceof ICPPASTTemplatedTypeTemplateParameter) {
return new CPPTemplateTemplateParameter(((ICPPASTTemplatedTypeTemplateParameter) templateParameter).getName()); return new CPPTemplateTemplateParameter(((ICPPASTTemplatedTypeTemplateParameter) tp).getName(), tp.isParameterPack());
} }
assert templateParameter instanceof ICPPASTParameterDeclaration; assert tp instanceof ICPPASTParameterDeclaration;
final IASTDeclarator dtor = ((ICPPASTParameterDeclaration) templateParameter).getDeclarator(); final IASTDeclarator dtor = ((ICPPASTParameterDeclaration) tp).getDeclarator();
return new CPPTemplateNonTypeParameter(ASTQueries.findInnermostDeclarator(dtor).getName()); return new CPPTemplateNonTypeParameter(ASTQueries.findInnermostDeclarator(dtor).getName());
} }
@ -708,15 +715,15 @@ public class CPPTemplates {
ICPPTemplateInstance instance = null; ICPPTemplateInstance instance = null;
if (template instanceof ICPPClassType) { if (template instanceof ICPPClassType) {
instance = new CPPClassInstance(owner, (ICPPClassType) template, tpMap, args); instance = new CPPClassInstance((ICPPClassType) template, owner, tpMap, args);
} else if (owner instanceof ICPPClassType && template instanceof ICPPMethod) { } else if (owner instanceof ICPPClassType && template instanceof ICPPMethod) {
if (template instanceof ICPPConstructor) { if (template instanceof ICPPConstructor) {
instance = new CPPConstructorInstance((ICPPClassType) owner, (ICPPConstructor) template, tpMap, args); instance = new CPPConstructorInstance((ICPPConstructor) template, (ICPPClassType) owner, tpMap, args);
} else { } else {
instance = new CPPMethodInstance((ICPPClassType) owner, (ICPPMethod) template, tpMap, args); instance = new CPPMethodInstance((ICPPMethod) template, (ICPPClassType) owner, tpMap, args);
} }
} else if (template instanceof ICPPFunction) { } else if (template instanceof ICPPFunction) {
instance = new CPPFunctionInstance(owner, (ICPPFunction) template, tpMap, args); instance = new CPPFunctionInstance((ICPPFunction) template, owner, tpMap, args);
} }
return instance; return instance;
} }
@ -739,17 +746,17 @@ public class CPPTemplates {
spec = new CPPFieldSpecialization(decl, owner, tpMap); spec = new CPPFieldSpecialization(decl, owner, tpMap);
} else if (decl instanceof ICPPFunctionTemplate) { } else if (decl instanceof ICPPFunctionTemplate) {
if (decl instanceof ICPPConstructor) if (decl instanceof ICPPConstructor)
spec = new CPPConstructorTemplateSpecialization(decl, owner, tpMap); spec = new CPPConstructorTemplateSpecialization((ICPPConstructor) decl, owner, tpMap);
else if (decl instanceof ICPPMethod) else if (decl instanceof ICPPMethod)
spec = new CPPMethodTemplateSpecialization(decl, owner, tpMap); spec = new CPPMethodTemplateSpecialization((ICPPMethod) decl, owner, tpMap);
else else
spec = new CPPFunctionTemplateSpecialization(decl, owner, tpMap); spec = new CPPFunctionTemplateSpecialization((ICPPFunctionTemplate) decl, owner, tpMap);
} else if (decl instanceof ICPPConstructor) { } else if (decl instanceof ICPPConstructor) {
spec = new CPPConstructorSpecialization(decl, owner, tpMap); spec = new CPPConstructorSpecialization((ICPPConstructor) decl, owner, tpMap);
} else if (decl instanceof ICPPMethod) { } else if (decl instanceof ICPPMethod) {
spec = new CPPMethodSpecialization(decl, owner, tpMap); spec = new CPPMethodSpecialization((ICPPMethod) decl, owner, tpMap);
} else if (decl instanceof ICPPFunction) { } else if (decl instanceof ICPPFunction) {
spec = new CPPFunctionSpecialization(decl, owner, tpMap); spec = new CPPFunctionSpecialization((ICPPFunction) decl, owner, tpMap);
} else if (decl instanceof ITypedef) { } else if (decl instanceof ITypedef) {
spec = new CPPTypedefSpecialization(decl, owner, tpMap); spec = new CPPTypedefSpecialization(decl, owner, tpMap);
} else if (decl instanceof IEnumeration || decl instanceof IEnumerator) { } else if (decl instanceof IEnumeration || decl instanceof IEnumerator) {
@ -815,7 +822,7 @@ public class CPPTemplates {
if (ret == r && params == ps) { if (ret == r && params == ps) {
return type; return type;
} }
return new CPPFunctionType(ret, params, ft.isConst(), ft.isVolatile()); return new CPPFunctionType(ret, params, ft.isConst(), ft.isVolatile(), ft.takesVarArgs());
} }
if (type instanceof ICPPTemplateParameter) { if (type instanceof ICPPTemplateParameter) {
@ -2105,7 +2112,16 @@ public class CPPTemplates {
if (arg.isNonTypeValue()) if (arg.isNonTypeValue())
return false; return false;
IType argType= arg.getTypeValue(); IType argType= arg.getTypeValue();
if (argType == null || !argType.isSameType((IType) par)) if (argType == null)
return false;
if (par.isParameterPack()) {
if (!(argType instanceof ICPPParameterPackType))
return false;
argType= ((ICPPParameterPackType) argType).getType();
if (argType == null)
return false;
}
if (!argType.isSameType((IType) par))
return false; return false;
} else { } else {
if (arg.isTypeValue()) if (arg.isTypeValue())

View file

@ -13,9 +13,7 @@
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp.semantics; package org.eclipse.cdt.internal.core.dom.parser.cpp.semantics;
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.*;
import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.getUltimateType;
import static org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil.getUltimateTypeUptoPointers;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty; import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
@ -66,7 +64,6 @@ import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.ICompositeType; import org.eclipse.cdt.core.dom.ast.ICompositeType;
import org.eclipse.cdt.core.dom.ast.IEnumeration; import org.eclipse.cdt.core.dom.ast.IEnumeration;
import org.eclipse.cdt.core.dom.ast.IEnumerator; 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.IFunctionType;
import org.eclipse.cdt.core.dom.ast.ILabel; import org.eclipse.cdt.core.dom.ast.ILabel;
import org.eclipse.cdt.core.dom.ast.IParameter; import org.eclipse.cdt.core.dom.ast.IParameter;
@ -84,6 +81,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConstructorChainInitializer;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTConversionName; 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.ICPPASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTExplicitTemplateInstantiation;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFieldReference;
@ -106,6 +104,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplatedTypeTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypeId;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTypenameExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTUsingDirective;
@ -157,6 +156,7 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPMethodTemplate;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPNamespace; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPNamespace;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPNamespaceAlias; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPNamespaceAlias;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameter; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameter;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType;
@ -556,7 +556,7 @@ public class CPPVisitor extends ASTQueries {
parent = param.getParent(); parent = param.getParent();
if (parent instanceof IASTStandardFunctionDeclarator) { if (parent instanceof IASTStandardFunctionDeclarator) {
IASTStandardFunctionDeclarator fdtor = (IASTStandardFunctionDeclarator) param.getParent(); IASTStandardFunctionDeclarator fdtor = (IASTStandardFunctionDeclarator) param.getParent();
// if the fdtor does not declare a function we don't create a binding for the parameter. // Create parameter bindings only if the declarator declares a function
if (!(findOutermostDeclarator(fdtor).getParent() instanceof IASTDeclaration) || if (!(findOutermostDeclarator(fdtor).getParent() instanceof IASTDeclaration) ||
findTypeRelevantDeclarator(fdtor) != fdtor) findTypeRelevantDeclarator(fdtor) != fdtor)
return null; return null;
@ -660,8 +660,8 @@ public class CPPVisitor extends ASTQueries {
} }
if (isFunction) { if (isFunction) {
if (binding instanceof ICPPInternalBinding && binding instanceof IFunction && name.isActive()) { if (binding instanceof ICPPInternalBinding && binding instanceof ICPPFunction && name.isActive()) {
IFunction function = (IFunction) binding; ICPPFunction function = (ICPPFunction) binding;
if (CPPSemantics.isSameFunction(function, typeRelevantDtor)) { if (CPPSemantics.isSameFunction(function, typeRelevantDtor)) {
binding= CPPSemantics.checkDeclSpecifier(binding, name, parent); binding= CPPSemantics.checkDeclSpecifier(binding, name, parent);
if (binding instanceof IProblemBinding) if (binding instanceof IProblemBinding)
@ -1547,22 +1547,14 @@ public class CPPVisitor extends ASTQueries {
pTypes[i] = pt; pTypes[i] = pt;
} }
return new CPPFunctionType(returnType, pTypes, isConst, isVolatile); return new CPPFunctionType(returnType, pTypes, isConst, isVolatile, false);
} }
private static IType createType(IType returnType, ICPPASTFunctionDeclarator fnDtor) { private static IType createType(IType returnType, ICPPASTFunctionDeclarator fnDtor) {
IASTParameterDeclaration[] params = fnDtor.getParameters(); ICPPASTParameterDeclaration[] params = fnDtor.getParameters();
IType[] pTypes = new IType[params.length]; IType[] pTypes = new IType[params.length];
IType pt = null;
for (int i = 0; i < params.length; i++) { for (int i = 0; i < params.length; i++) {
IASTDeclSpecifier pDeclSpec = params[i].getDeclSpecifier(); pTypes[i]= createParameterType(params[i], true);
IASTDeclarator pDtor = params[i].getDeclarator();
pt = createType(pDeclSpec);
pt = createType(pt, pDtor);
pt = SemanticUtil.adjustParameterType(pt, true);
pTypes[i] = pt;
} }
IASTName name = fnDtor.getName(); IASTName name = fnDtor.getName();
@ -1576,7 +1568,8 @@ public class CPPVisitor extends ASTQueries {
returnType = getPointerTypes(returnType, fnDtor); returnType = getPointerTypes(returnType, fnDtor);
} }
IType type = new CPPFunctionType(returnType, pTypes, fnDtor.isConst(), fnDtor.isVolatile()); CPPFunctionType type = new CPPFunctionType(returnType, pTypes, fnDtor.isConst(), fnDtor.isVolatile(),
fnDtor.takesVarArgs());
final IASTDeclarator nested = fnDtor.getNestedDeclarator(); final IASTDeclarator nested = fnDtor.getNestedDeclarator();
if (nested != null) { if (nested != null) {
return createType(type, nested); return createType(type, nested);
@ -1584,6 +1577,47 @@ public class CPPVisitor extends ASTQueries {
return type; return type;
} }
/**
* Creates the type for a parameter declaration.
*/
public static IType createParameterType(final ICPPASTParameterDeclaration pdecl, boolean forFuncType) {
IType pt;
IASTDeclSpecifier pDeclSpec = pdecl.getDeclSpecifier();
ICPPASTDeclarator pDtor = pdecl.getDeclarator();
pt = createType(pDeclSpec);
pt = createType(pt, pDtor);
pt= adjustParameterType(pt, forFuncType);
if (CPPVisitor.findInnermostDeclarator(pDtor).declaresParameterPack()) {
pt= new CPPParameterPackType(pt);
}
return pt;
}
/**
* Adjusts the parameter type according to 8.3.5-3:
* cv-qualifiers are deleted, arrays and function types are converted to pointers.
*/
private static IType adjustParameterType(final IType pt, boolean forFunctionType) {
// bug 239975
IType t= SemanticUtil.getNestedType(pt, TDEF);
if (t instanceof IArrayType) {
IArrayType at = (IArrayType) t;
return new CPPPointerType(at.getType());
}
if (t instanceof IFunctionType) {
return new CPPPointerType(pt);
}
// 8.3.5-3
// Any cv-qualifier modifying a parameter type is deleted. The parameter type remains
// to be qualified.
if (forFunctionType && SemanticUtil.getCVQualifier(t) != CVQualifier._) {
return SemanticUtil.getNestedType(t, TDEF | ALLCVQ);
}
return pt;
}
/** /**
* @param declarator * @param declarator
* @return * @return
@ -1652,14 +1686,18 @@ public class CPPVisitor extends ASTQueries {
IASTNode parent = declarator.getParent(); IASTNode parent = declarator.getParent();
IASTDeclSpecifier declSpec = null; IASTDeclSpecifier declSpec = null;
if (parent instanceof IASTParameterDeclaration) { boolean isPackExpansion= false;
declSpec = ((IASTParameterDeclaration) parent).getDeclSpecifier(); if (parent instanceof IASTSimpleDeclaration) {
} else if (parent instanceof IASTSimpleDeclaration) {
declSpec = ((IASTSimpleDeclaration)parent).getDeclSpecifier(); declSpec = ((IASTSimpleDeclaration)parent).getDeclSpecifier();
} else if (parent instanceof IASTFunctionDefinition) { } else if (parent instanceof IASTFunctionDefinition) {
declSpec = ((IASTFunctionDefinition)parent).getDeclSpecifier(); declSpec = ((IASTFunctionDefinition)parent).getDeclSpecifier();
} else if (parent instanceof IASTTypeId) { } else if (parent instanceof ICPPASTTypeId) {
declSpec = ((IASTTypeId)parent).getDeclSpecifier(); final ICPPASTTypeId typeId = (ICPPASTTypeId)parent;
declSpec = typeId.getDeclSpecifier();
isPackExpansion= typeId.isPackExpansion();
} else {
assert false;
return null;
} }
IType type = createType(declSpec); IType type = createType(declSpec);
@ -1676,6 +1714,9 @@ public class CPPVisitor extends ASTQueries {
} }
} }
} }
if (isPackExpansion) {
type= new CPPParameterPackType(type);
}
return type; return type;
} }
@ -2154,4 +2195,8 @@ public class CPPVisitor extends ASTQueries {
} }
return false; return false;
} }
public static ICPPASTDeclarator findInnermostDeclarator(ICPPASTDeclarator dtor) {
return (ICPPASTDeclarator) ASTQueries.findInnermostDeclarator(dtor);
}
} }

View file

@ -27,7 +27,6 @@ import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IEnumeration; import org.eclipse.cdt.core.dom.ast.IEnumeration;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IParameter;
import org.eclipse.cdt.core.dom.ast.IPointerType; import org.eclipse.cdt.core.dom.ast.IPointerType;
import org.eclipse.cdt.core.dom.ast.IProblemBinding; import org.eclipse.cdt.core.dom.ast.IProblemBinding;
import org.eclipse.cdt.core.dom.ast.IQualifierType; import org.eclipse.cdt.core.dom.ast.IQualifierType;
@ -40,7 +39,6 @@ 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.ICPPConstructor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod; 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.ICPPPointerToMemberType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization; import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization;
@ -136,13 +134,7 @@ public class Conversions {
// shall be an rvalue. // shall be an rvalue.
boolean ok; boolean ok;
if (isLValueRef) { if (isLValueRef) {
// mstodo ok = getCVQualifier(cv1T1) == CVQualifier.c;
// Special rule for implicit object type, 13.3.1-5:
// Even if the implicit object type is not const-qualified, an rvalue temporary can
// be bound to the parameter as long as in all other respects ....
//
final CVQualifier cvq = getCVQualifier(cv1T1);
ok = cvq == CVQualifier.c;
} else { } else {
ok= !exprIsLValue; ok= !exprIsLValue;
} }
@ -467,16 +459,13 @@ public class Conversions {
continue; continue;
} }
} else { } else {
IType ptype= ptypes[0]; IType ptype= SemanticUtil.getNestedType(ptypes[0], TDEF);
// We don't need to check the implicit conversion sequence if the type is void // We don't need to check the implicit conversion sequence if the type is void
if (ptype instanceof ICPPBasicType && ((ICPPBasicType) ptype).getKind() == Kind.eVoid) if (SemanticUtil.isVoidType(ptype))
continue; continue;
if (ptypes.length > 1) { if (ctor.getRequiredArgumentCount() > 1)
IParameter[] pars = ctor.getParameters();
if (pars.length < 2 || !((ICPPParameter) pars[1]).hasDefaultValue())
continue; continue;
}
c1= new FunctionCost(ctor, checkImplicitConversionSequence(ptype, source, sourceIsLValue, UDCMode.noUDC, false)); c1= new FunctionCost(ctor, checkImplicitConversionSequence(ptype, source, sourceIsLValue, UDCMode.noUDC, false));
} }
int cmp= c1.compareTo(null, cost1); int cmp= c1.compareTo(null, cost1);
@ -868,7 +857,7 @@ public class Conversions {
// 4.10-2 an rvalue of type "pointer to cv T", where T is an object type can be // 4.10-2 an rvalue of type "pointer to cv T", where T is an object type can be
// converted to an rvalue of type "pointer to cv void" // converted to an rvalue of type "pointer to cv void"
IType tgtPtrTgt= getNestedType(tgtPtr.getType(), TDEF | CVTYPE | REF); IType tgtPtrTgt= getNestedType(tgtPtr.getType(), TDEF | CVTYPE | REF);
if (tgtPtrTgt instanceof IBasicType && ((IBasicType) tgtPtrTgt).getKind() == Kind.eVoid) { if (SemanticUtil.isVoidType(tgtPtrTgt)) {
cost.setRank(Rank.CONVERSION); cost.setRank(Rank.CONVERSION);
cost.setInheritanceDistance(Short.MAX_VALUE); // mstodo add distance to last base class cost.setInheritanceDistance(Short.MAX_VALUE); // mstodo add distance to last base class
CVQualifier cv= getCVQualifier(srcPtr.getType()); CVQualifier cv= getCVQualifier(srcPtr.getType());

View file

@ -36,7 +36,6 @@ import org.eclipse.cdt.core.dom.ast.IASTInitializer;
import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNamedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.IASTNamedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration; import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTTypeId; import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression; import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression;
@ -56,6 +55,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceDefinition; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNewExpression; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNewExpression;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTQualifiedName; 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.ICPPASTTemplateDeclaration;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId; import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateId;
@ -598,12 +598,12 @@ public class LookupData {
public IType[] getFunctionArgumentTypes() { public IType[] getFunctionArgumentTypes() {
if (functionArgTypes == null && functionArgs != null) { if (functionArgTypes == null && functionArgs != null) {
if (functionArgs instanceof IASTParameterDeclaration[]) { if (functionArgs instanceof ICPPASTParameterDeclaration[]) {
IASTParameterDeclaration[] pdecls= (IASTParameterDeclaration[]) functionArgs; ICPPASTParameterDeclaration[] pdecls= (ICPPASTParameterDeclaration[]) functionArgs;
functionArgTypes= new IType[pdecls.length]; functionArgTypes= new IType[pdecls.length];
for (int i = 0; i < pdecls.length; i++) { for (int i = 0; i < pdecls.length; i++) {
IASTParameterDeclaration p = pdecls[i]; functionArgTypes[i] = SemanticUtil.getSimplifiedType(CPPVisitor.createParameterType(
functionArgTypes[i]= SemanticUtil.getSimplifiedType(CPPVisitor.createType(p.getDeclarator())); pdecls[i], true));
} }
} else if (functionArgs instanceof IASTExpression[]) { } else if (functionArgs instanceof IASTExpression[]) {
IASTExpression[] exprs= (IASTExpression[]) functionArgs; IASTExpression[] exprs= (IASTExpression[]) functionArgs;
@ -647,7 +647,7 @@ public class LookupData {
functionArgTypes= paramTypes; functionArgTypes= paramTypes;
} }
public void setFunctionParameters(IASTParameterDeclaration[] parameters) { public void setFunctionParameters(ICPPASTParameterDeclaration[] parameters) {
functionArgs= parameters; functionArgs= parameters;
} }

View file

@ -20,6 +20,7 @@ import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit; import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.dom.ast.IArrayType; import org.eclipse.cdt.core.dom.ast.IArrayType;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IPointerType; import org.eclipse.cdt.core.dom.ast.IPointerType;
@ -27,14 +28,17 @@ import org.eclipse.cdt.core.dom.ast.IProblemBinding;
import org.eclipse.cdt.core.dom.ast.IQualifierType; import org.eclipse.cdt.core.dom.ast.IQualifierType;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.ITypedef; import org.eclipse.cdt.core.dom.ast.ITypedef;
import org.eclipse.cdt.core.dom.ast.IBasicType.Kind;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPBase; import org.eclipse.cdt.core.dom.ast.cpp.ICPPBase;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod; import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
import org.eclipse.cdt.core.index.IIndexBinding; import org.eclipse.cdt.core.index.IIndexBinding;
import org.eclipse.cdt.core.parser.Keywords; import org.eclipse.cdt.core.parser.Keywords;
import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.ArrayUtil;
@ -49,6 +53,7 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPTemplateArgument; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPTemplateArgument;
import org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPDeferredClassInstance; import org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPDeferredClassInstance;
import org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPUnknownBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.OverloadableOperator; import org.eclipse.cdt.internal.core.dom.parser.cpp.OverloadableOperator;
/** /**
@ -288,6 +293,7 @@ public class SemanticUtil {
return replaceNestedType((ITypeContainer) rt, newNested); return replaceNestedType((ITypeContainer) rt, newNested);
} }
} }
// Pack expansion types are dependent types, there is no need to descend into those.
if (t == null) if (t == null)
return type; return type;
@ -310,7 +316,7 @@ public class SemanticUtil {
if (ret == r && params == ps) { if (ret == r && params == ps) {
return type; return type;
} }
return new CPPFunctionType(ret, params, ft.isConst(), ft.isVolatile()); return new CPPFunctionType(ret, params, ft.isConst(), ft.isVolatile(), ft.takesVarArgs());
} }
if (type instanceof ITypedef) { if (type instanceof ITypedef) {
@ -371,6 +377,50 @@ public class SemanticUtil {
return type; return type;
} }
public static boolean containsParameterPack(IType type) {
while (true) {
if (type instanceof ICPPTemplateParameter) {
return ((ICPPTemplateParameter) type).isParameterPack();
} else if (type instanceof ICPPDeferredClassInstance) {
// mstodo check the deferred arguments.
return false;
} else if (type instanceof ICPPUnknownBinding) {
try {
IBinding owner= ((ICPPUnknownBinding) type).getOwner();
if (owner instanceof IType) {
type= (IType) owner;
} else {
return false;
}
} catch (DOMException e) {
return false;
}
} else if (type instanceof IFunctionType) {
final ICPPFunctionType ft = (ICPPFunctionType) type;
final IType r = ft.getReturnType();
if (containsParameterPack(r))
return true;
final IType[] ps = ft.getParameterTypes();
for (IType p : ps) {
if (containsParameterPack(p))
return true;
}
} else if (type instanceof ICPPParameterPackType) {
// A pack expansion expands all packs.
return false;
} else if (type instanceof IArrayType) {
final IArrayType atype= (IArrayType) type;
// mstodo check array size
type= atype.getType();
} else if (type instanceof ITypeContainer) {
type= ((ITypeContainer) type).getType();
} else {
return false;
}
}
}
public static IType mapToAST(IType type, IASTNode node) { public static IType mapToAST(IType type, IASTNode node) {
if (type instanceof IFunctionType) { if (type instanceof IFunctionType) {
final ICPPFunctionType ft = (ICPPFunctionType) type; final ICPPFunctionType ft = (ICPPFunctionType) type;
@ -379,7 +429,7 @@ public class SemanticUtil {
if (ret == r) { if (ret == r) {
return type; return type;
} }
return new CPPFunctionType(ret, ft.getParameterTypes(), ft.isConst(), ft.isVolatile()); return new CPPFunctionType(ret, ft.getParameterTypes(), ft.isConst(), ft.isVolatile(), ft.takesVarArgs());
} }
if (type instanceof ITypeContainer) { if (type instanceof ITypeContainer) {
final ITypeContainer tc = (ITypeContainer) type; final ITypeContainer tc = (ITypeContainer) type;
@ -453,30 +503,6 @@ public class SemanticUtil {
return arg; return arg;
} }
/**
* Adjusts the parameter type according to 8.3.5-3:
* cv-qualifiers are deleted, arrays and function types are converted to pointers.
*/
public static IType adjustParameterType(final IType pt, boolean forFunctionType) {
// bug 239975
IType t= SemanticUtil.getNestedType(pt, TDEF);
if (t instanceof IArrayType) {
IArrayType at = (IArrayType) t;
return new CPPPointerType(at.getType());
}
if (t instanceof IFunctionType) {
return new CPPPointerType(pt);
}
// 8.3.5-3
// Any cv-qualifier modifying a parameter type is deleted. The parameter type remains
// to be qualified.
if (forFunctionType && SemanticUtil.getCVQualifier(t) != CVQualifier._) {
return SemanticUtil.getNestedType(t, TDEF | ALLCVQ);
}
return pt;
}
public static IType addQualifiers(IType baseType, boolean cnst, boolean vol) { public static IType addQualifiers(IType baseType, boolean cnst, boolean vol) {
if (cnst || vol) { if (cnst || vol) {
if (baseType instanceof IQualifierType) { if (baseType instanceof IQualifierType) {
@ -550,4 +576,14 @@ public class SemanticUtil {
} }
return false; return false;
} }
public static boolean isVoidType(IType ptype) {
while (ptype instanceof ITypedef) {
ptype= ((ITypedef) ptype).getType();
}
if (ptype instanceof IBasicType) {
return ((IBasicType) ptype).getKind() == Kind.eVoid;
}
return false;
}
} }

View file

@ -70,6 +70,7 @@ public class ExpressionWriter extends NodeWriter{
private static final String TYPEID_OP = "typeid ("; //$NON-NLS-1$ private static final String TYPEID_OP = "typeid ("; //$NON-NLS-1$
private static final String OPEN_BRACKET_OP = "("; //$NON-NLS-1$ private static final String OPEN_BRACKET_OP = "("; //$NON-NLS-1$
private static final String SIZEOF_OP = "sizeof "; //$NON-NLS-1$ private static final String SIZEOF_OP = "sizeof "; //$NON-NLS-1$
private static final String SIZEOF_PARAMETER_PACK_OP = "sizeof... "; //$NON-NLS-1$
private static final String NOT_OP = "!"; //$NON-NLS-1$ private static final String NOT_OP = "!"; //$NON-NLS-1$
private static final String TILDE_OP = "~"; //$NON-NLS-1$ private static final String TILDE_OP = "~"; //$NON-NLS-1$
private static final String AMPERSAND_OP = "&"; //$NON-NLS-1$ private static final String AMPERSAND_OP = "&"; //$NON-NLS-1$
@ -247,6 +248,7 @@ public class ExpressionWriter extends NodeWriter{
case IASTUnaryExpression.op_tilde: case IASTUnaryExpression.op_tilde:
case IASTUnaryExpression.op_not: case IASTUnaryExpression.op_not:
case IASTUnaryExpression.op_sizeof: case IASTUnaryExpression.op_sizeof:
case IASTUnaryExpression.op_sizeofParameterPack:
case IASTUnaryExpression.op_bracketedPrimary: case IASTUnaryExpression.op_bracketedPrimary:
case ICPPASTUnaryExpression.op_throw: case ICPPASTUnaryExpression.op_throw:
case ICPPASTUnaryExpression.op_typeid: case ICPPASTUnaryExpression.op_typeid:
@ -296,6 +298,8 @@ public class ExpressionWriter extends NodeWriter{
return NOT_OP; return NOT_OP;
case IASTUnaryExpression.op_sizeof: case IASTUnaryExpression.op_sizeof:
return SIZEOF_OP; return SIZEOF_OP;
case IASTUnaryExpression.op_sizeofParameterPack:
return SIZEOF_PARAMETER_PACK_OP;
case IASTUnaryExpression.op_bracketedPrimary: case IASTUnaryExpression.op_bracketedPrimary:
return OPEN_BRACKET_OP; return OPEN_BRACKET_OP;
case ICPPASTUnaryExpression.op_throw: case ICPPASTUnaryExpression.op_throw:

View file

@ -16,19 +16,19 @@ package org.eclipse.cdt.internal.core.index;
import org.eclipse.cdt.core.CCorePlugin; import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.dom.ast.ASTTypeUtil; import org.eclipse.cdt.core.dom.ast.ASTTypeUtil;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IFunction; import org.eclipse.cdt.core.dom.ast.IFunction;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.IBasicType.Kind;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassTemplatePartialSpecialization; import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassTemplatePartialSpecialization;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPConstructor; 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.ICPPFunctionType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod; import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateArgument;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance; import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateInstance;
import org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPUnknownClassInstance; import org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPUnknownClassInstance;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.SemanticUtil;
import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.CoreException;
/** /**
@ -59,8 +59,8 @@ public class IndexCPPSignatureUtil {
buffer.append(getTemplateArgString(partial.getTemplateArguments(), false)); buffer.append(getTemplateArgString(partial.getTemplateArguments(), false));
} }
if (binding instanceof IFunction) { if (binding instanceof ICPPFunction) {
IFunction function = (IFunction) binding; IFunction function = (ICPPFunction) binding;
buffer.append(getFunctionParameterString(function.getType())); buffer.append(getFunctionParameterString(function.getType()));
} }
if (binding instanceof ICPPMethod && !(binding instanceof ICPPConstructor)) { if (binding instanceof ICPPMethod && !(binding instanceof ICPPConstructor)) {
@ -86,20 +86,12 @@ public class IndexCPPSignatureUtil {
/** /**
* Constructs a string in the format: * Constructs a string in the format:
* (paramName1,paramName2,...) * (paramName1,paramName2,...)
*
* @param fType
* @return
* @throws DOMException
*/ */
private static String getFunctionParameterString(IFunctionType fType) throws DOMException { private static String getFunctionParameterString(IFunctionType functionType) throws DOMException {
IType[] types = fType.getParameterTypes(); IType[] types = functionType.getParameterTypes();
if (types.length == 1) { if (types.length == 1 && SemanticUtil.isVoidType(types[0])) {
if (types[0] instanceof IBasicType) {
if (((IBasicType) types[0]).getKind() == Kind.eVoid) {
types = new IType[0]; types = new IType[0];
} }
}
}
StringBuilder result = new StringBuilder(); StringBuilder result = new StringBuilder();
result.append('('); result.append('(');
for (int i= 0; i < types.length; i++) { for (int i= 0; i < types.length; i++) {
@ -108,6 +100,12 @@ public class IndexCPPSignatureUtil {
} }
result.append(ASTTypeUtil.getType(types[i])); result.append(ASTTypeUtil.getType(types[i]));
} }
if (functionType instanceof ICPPFunctionType && ((ICPPFunctionType) functionType).takesVarArgs()) {
if (types.length != 0) {
result.append(',');
}
result.append("..."); //$NON-NLS-1$
}
result.append(')'); result.append(')');
return result.toString(); return result.toString();
} }

View file

@ -38,6 +38,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPMethod;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceAlias; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceAlias;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceScope; import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameterPackType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter; import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPPointerToMemberType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType; import org.eclipse.cdt.core.dom.ast.cpp.ICPPReferenceType;
@ -56,6 +57,7 @@ import org.eclipse.cdt.core.index.IIndexMacroContainer;
import org.eclipse.cdt.internal.core.dom.parser.Value; import org.eclipse.cdt.internal.core.dom.parser.Value;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPArrayType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPArrayType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPFunctionType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPFunctionType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType;
@ -132,7 +134,7 @@ public class CPPCompositesFactory extends AbstractCompositeFactory {
IType[] p= ft.getParameterTypes(); IType[] p= ft.getParameterTypes();
IType[] p2= getCompositeTypes(p); IType[] p2= getCompositeTypes(p);
if (r != r2 || p != p2) { if (r != r2 || p != p2) {
return new CPPFunctionType(r2, p2, ft.isConst(), ft.isVolatile()); return new CPPFunctionType(r2, p2, ft.isConst(), ft.isVolatile(), ft.takesVarArgs());
} }
return ft; return ft;
} }
@ -165,6 +167,15 @@ public class CPPCompositesFactory extends AbstractCompositeFactory {
} }
return rt; return rt;
} }
if (rtype instanceof ICPPParameterPackType) {
ICPPParameterPackType rt= (ICPPParameterPackType) rtype;
IType r= rt.getType();
IType r2= getCompositeType(r);
if (r != r2) {
return new CPPParameterPackType(r2);
}
return rt;
}
if (rtype instanceof IQualifierType) { if (rtype instanceof IQualifierType) {
IQualifierType qt= (IQualifierType) rtype; IQualifierType qt= (IQualifierType) rtype;
IType r= qt.getType(); IType r= qt.getType();

View file

@ -76,6 +76,14 @@ class CompositeCPPFunction extends CompositeCPPBinding implements ICPPFunction {
return ((ICPPFunction)rbinding).takesVarArgs(); return ((ICPPFunction)rbinding).takesVarArgs();
} }
public int getRequiredArgumentCount() throws DOMException {
return ((ICPPFunction)rbinding).getRequiredArgumentCount();
}
public boolean hasParameterPack() {
return ((ICPPFunction)rbinding).hasParameterPack();
}
@Override @Override
public Object clone() { public Object clone() {
fail(); return null; fail(); return null;

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2007, 2008 Symbian Software Systems and others. * Copyright (c) 2007, 2009 Symbian Software Systems 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
@ -7,6 +7,7 @@
* *
* Contributors: * Contributors:
* Andrew Ferguson (Symbian) - Initial implementation * Andrew Ferguson (Symbian) - Initial implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.index.composite.cpp; package org.eclipse.cdt.internal.core.index.composite.cpp;
@ -22,4 +23,8 @@ class CompositeCPPParameter extends CompositeCPPVariable implements ICPPParamete
public boolean hasDefaultValue() { public boolean hasDefaultValue() {
return ((ICPPParameter)rbinding).hasDefaultValue(); return ((ICPPParameter)rbinding).hasDefaultValue();
} }
public boolean isParameterPack() {
return ((ICPPParameter)rbinding).isParameterPack();
}
} }

View file

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2008 Symbian Software Systems and others. * Copyright (c) 2008, 2009 Symbian Software Systems 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
@ -45,6 +45,10 @@ public class CompositeCPPTemplateNonTypeParameter extends CompositeCPPVariable i
return ((ICPPTemplateParameter)rbinding).getParameterID(); return ((ICPPTemplateParameter)rbinding).getParameterID();
} }
public boolean isParameterPack() {
return ((ICPPTemplateParameter)rbinding).isParameterPack();
}
public ICPPTemplateArgument getDefaultValue() { public ICPPTemplateArgument getDefaultValue() {
try { try {
return TemplateInstanceUtil.convert(cf, ((ICPPTemplateNonTypeParameter)rbinding).getDefaultValue()); return TemplateInstanceUtil.convert(cf, ((ICPPTemplateNonTypeParameter)rbinding).getDefaultValue());

View file

@ -60,6 +60,10 @@ public class CompositeCPPTemplateTemplateParameter extends CompositeCPPBinding
return ((ICPPTemplateParameter)rbinding).getParameterID(); return ((ICPPTemplateParameter)rbinding).getParameterID();
} }
public boolean isParameterPack() {
return ((ICPPTemplateParameter)rbinding).isParameterPack();
}
public boolean isSameType(IType type) { public boolean isSameType(IType type) {
return ((IType)rbinding).isSameType(type); return ((IType)rbinding).isSameType(type);
} }

View file

@ -50,6 +50,10 @@ public class CompositeCPPTemplateTypeParameter extends CompositeCPPBinding
return ((ICPPTemplateParameter)rbinding).getParameterID(); return ((ICPPTemplateParameter)rbinding).getParameterID();
} }
public boolean isParameterPack() {
return ((ICPPTemplateParameter)rbinding).isParameterPack();
}
public boolean isSameType(IType type) { public boolean isSameType(IType type) {
return ((IType)rbinding).isSameType(type); return ((IType)rbinding).isSameType(type);
} }

View file

@ -187,10 +187,11 @@ public class PDOM extends PlatformObject implements IPDOM {
* 92.0 - simplification of basic types, bug 231859. * 92.0 - simplification of basic types, bug 231859.
* 93.0 - further simplification of basic types, bug 231859. * 93.0 - further simplification of basic types, bug 231859.
* 94.0 - new model for storing types, bug 294306. * 94.0 - new model for storing types, bug 294306.
* 95.0 - parameter packs, bug 294730.
*/ */
private static final int MIN_SUPPORTED_VERSION= version(94, 0); private static final int MIN_SUPPORTED_VERSION= version(95, 0);
private static final int MAX_SUPPORTED_VERSION= version(94, Short.MAX_VALUE); private static final int MAX_SUPPORTED_VERSION= version(95, Short.MAX_VALUE);
private static final int DEFAULT_VERSION = version(94, 0); private static final int DEFAULT_VERSION = version(95, 0);
private static int version(int major, int minor) { private static int version(int major, int minor) {
return (major << 16) + minor; return (major << 16) + minor;

View file

@ -108,7 +108,7 @@ class PDOMCPPAnnotation {
* @param annotation Annotation containing visibility information. * @param annotation Annotation containing visibility information.
* @return The visibility component of the annotation. * @return The visibility component of the annotation.
*/ */
public static int getVisibility(byte annotation) { public static int getVisibility(int annotation) {
return (annotation >> VISIBILITY_OFFSET) & VISIBILITY_MASK; return (annotation >> VISIBILITY_OFFSET) & VISIBILITY_MASK;
} }
} }

View file

@ -38,6 +38,8 @@ import org.eclipse.core.runtime.CoreException;
*/ */
class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverloader { class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverloader {
private static final short ANNOT_PARAMETER_PACK = 0x100;
/** /**
* Offset of total number of function parameters (relative to the * Offset of total number of function parameters (relative to the
* beginning of the record). * beginning of the record).
@ -70,15 +72,18 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
* Offset of annotation information (relative to the beginning of the * Offset of annotation information (relative to the beginning of the
* record). * record).
*/ */
private static final int ANNOTATION = EXCEPTION_SPEC + Database.PTR_SIZE; // byte private static final int ANNOTATION = EXCEPTION_SPEC + Database.PTR_SIZE; // short
private static final int REQUIRED_ARG_COUNT = ANNOTATION + 2;
/** /**
* The size in bytes of a PDOMCPPFunction record in the database. * The size in bytes of a PDOMCPPFunction record in the database.
*/ */
@SuppressWarnings("hiding") @SuppressWarnings("hiding")
protected static final int RECORD_SIZE = ANNOTATION + 1; protected static final int RECORD_SIZE = REQUIRED_ARG_COUNT + 4;
private byte annotation= -1; private short fAnnotation= -1;
private int fRequiredArgCount= -1;
private ICPPFunctionType fType; private ICPPFunctionType fType;
public PDOMCPPFunction(PDOMLinkage linkage, PDOMNode parent, ICPPFunction function, boolean setTypes) throws CoreException, DOMException { public PDOMCPPFunction(PDOMLinkage linkage, PDOMNode parent, ICPPFunction function, boolean setTypes) throws CoreException, DOMException {
@ -86,13 +91,21 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
Database db = getDB(); Database db = getDB();
Integer sigHash = IndexCPPSignatureUtil.getSignatureHash(function); Integer sigHash = IndexCPPSignatureUtil.getSignatureHash(function);
getDB().putInt(record + SIGNATURE_HASH, sigHash != null ? sigHash.intValue() : 0); getDB().putInt(record + SIGNATURE_HASH, sigHash != null ? sigHash.intValue() : 0);
db.putByte(record + ANNOTATION, PDOMCPPAnnotation.encodeAnnotation(function)); db.putShort(record + ANNOTATION, getAnnotation(function));
db.putInt(record + REQUIRED_ARG_COUNT, function.getRequiredArgumentCount());
if (setTypes) { if (setTypes) {
initData(function.getType(), function.getParameters(), extractExceptionSpec(function)); initData(function.getType(), function.getParameters(), extractExceptionSpec(function));
} }
} }
private short getAnnotation(ICPPFunction function) throws DOMException {
int annot= PDOMCPPAnnotation.encodeAnnotation(function);
if (function.hasParameterPack()) {
annot |= ANNOT_PARAMETER_PACK;
}
return (short) annot;
}
public void initData(ICPPFunctionType ftype, ICPPParameter[] params, IType[] exceptionSpec) { public void initData(ICPPFunctionType ftype, ICPPParameter[] params, IType[] exceptionSpec) {
try { try {
setType(ftype); setType(ftype);
@ -109,11 +122,13 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
ICPPFunction func= (ICPPFunction) newBinding; ICPPFunction func= (ICPPFunction) newBinding;
ICPPFunctionType newType; ICPPFunctionType newType;
ICPPParameter[] newParams; ICPPParameter[] newParams;
byte newAnnotation; short newAnnotation;
int newBindingRequiredArgCount;
try { try {
newType= func.getType(); newType= func.getType();
newParams = func.getParameters(); newParams = func.getParameters();
newAnnotation = PDOMCPPAnnotation.encodeAnnotation(func); newAnnotation = getAnnotation(func);
newBindingRequiredArgCount= func.getRequiredArgumentCount();
} catch (DOMException e) { } catch (DOMException e) {
throw new CoreException(Util.createStatus(e)); throw new CoreException(Util.createStatus(e));
} }
@ -122,23 +137,35 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
linkage.storeType(record+FUNCTION_TYPE, newType); linkage.storeType(record+FUNCTION_TYPE, newType);
PDOMCPPParameter oldParams= getFirstParameter(null); PDOMCPPParameter oldParams= getFirstParameter(null);
int requiredCount;
if (oldParams != null && hasDeclaration()) { if (oldParams != null && hasDeclaration()) {
int parCount= 0;
requiredCount= 0;
for (ICPPParameter newPar : newParams) { for (ICPPParameter newPar : newParams) {
parCount++;
if (parCount <= newBindingRequiredArgCount && !oldParams.hasDefaultValue())
requiredCount= parCount;
oldParams.update(newPar); oldParams.update(newPar);
long next= oldParams.getNextPtr(); long next= oldParams.getNextPtr();
if (next == 0) if (next == 0)
break; break;
oldParams= new PDOMCPPParameter(linkage, next, null); oldParams= new PDOMCPPParameter(linkage, next, null);
} }
if (parCount < newBindingRequiredArgCount) {
requiredCount= newBindingRequiredArgCount;
}
} else { } else {
requiredCount= newBindingRequiredArgCount;
setParameters(newParams); setParameters(newParams);
if (oldParams != null) { if (oldParams != null) {
oldParams.delete(linkage); oldParams.delete(linkage);
} }
} }
final Database db = getDB(); final Database db = getDB();
db.putByte(record + ANNOTATION, newAnnotation); db.putShort(record + ANNOTATION, newAnnotation);
annotation= newAnnotation; fAnnotation= newAnnotation;
db.putInt(record + REQUIRED_ARG_COUNT, requiredCount);
fRequiredArgCount= requiredCount;
long oldRec = db.getRecPtr(record+EXCEPTION_SPEC); long oldRec = db.getRecPtr(record+EXCEPTION_SPEC);
storeExceptionSpec(extractExceptionSpec(func)); storeExceptionSpec(extractExceptionSpec(func));
@ -213,14 +240,31 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
return rec != 0 ? new PDOMCPPParameter(getLinkage(), rec, type) : null; return rec != 0 ? new PDOMCPPParameter(getLinkage(), rec, type) : null;
} }
public boolean isInline() throws DOMException { public boolean isInline() {
return getBit(getAnnotation(), PDOMCAnnotation.INLINE_OFFSET); return getBit(getAnnotation(), PDOMCAnnotation.INLINE_OFFSET);
} }
final protected byte getAnnotation() {
if (annotation == -1) public int getRequiredArgumentCount() throws DOMException {
annotation= getByte(record + ANNOTATION); if (fRequiredArgCount == -1) {
return annotation; try {
fRequiredArgCount= getDB().getInt(record + REQUIRED_ARG_COUNT);
} catch (CoreException e) {
fRequiredArgCount= 0;
}
}
return fRequiredArgCount;
}
final protected short getAnnotation() {
if (fAnnotation == -1) {
try {
fAnnotation= getDB().getShort(record + ANNOTATION);
} catch (CoreException e) {
fAnnotation= 0;
}
}
return fAnnotation;
} }
public boolean isExternC() throws DOMException { public boolean isExternC() throws DOMException {
@ -270,21 +314,21 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
return fType; return fType;
} }
public boolean isAuto() throws DOMException { public boolean isAuto() {
// ISO/IEC 14882:2003 7.1.1.2 // ISO/IEC 14882:2003 7.1.1.2
return false; return false;
} }
public boolean isExtern() throws DOMException { public boolean isExtern() {
return getBit(getAnnotation(), PDOMCAnnotation.EXTERN_OFFSET); return getBit(getAnnotation(), PDOMCAnnotation.EXTERN_OFFSET);
} }
public boolean isRegister() throws DOMException { public boolean isRegister() {
// ISO/IEC 14882:2003 7.1.1.2 // ISO/IEC 14882:2003 7.1.1.2
return false; return false;
} }
public boolean isStatic() throws DOMException { public boolean isStatic() {
return getBit(getAnnotation(), PDOMCAnnotation.STATIC_OFFSET); return getBit(getAnnotation(), PDOMCAnnotation.STATIC_OFFSET);
} }
@ -292,6 +336,10 @@ class PDOMCPPFunction extends PDOMCPPBinding implements ICPPFunction, IPDOMOverl
return getBit(getAnnotation(), PDOMCAnnotation.VARARGS_OFFSET); return getBit(getAnnotation(), PDOMCAnnotation.VARARGS_OFFSET);
} }
public boolean hasParameterPack() {
return getBit(getAnnotation(), ANNOT_PARAMETER_PACK);
}
@Override @Override
public Object clone() { public Object clone() {
throw new PDOMNotImplementedError(); throw new PDOMNotImplementedError();

View file

@ -14,7 +14,6 @@ package org.eclipse.cdt.internal.core.pdom.dom.cpp;
import org.eclipse.cdt.core.CCorePlugin; import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.dom.ast.DOMException; import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IFunctionType; import org.eclipse.cdt.core.dom.ast.IFunctionType;
import org.eclipse.cdt.core.dom.ast.IParameter;
import org.eclipse.cdt.core.dom.ast.IScope; import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.IType; import org.eclipse.cdt.core.dom.ast.IType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunction; import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunction;
@ -63,41 +62,62 @@ class PDOMCPPFunctionSpecialization extends PDOMCPPSpecialization implements ICP
* Offset of annotation information (relative to the beginning of the * Offset of annotation information (relative to the beginning of the
* record). * record).
*/ */
protected static final int ANNOTATION = EXCEPTION_SPEC + Database.PTR_SIZE; // byte protected static final int ANNOTATION_OFFSET = EXCEPTION_SPEC + Database.PTR_SIZE; // short
private static final int REQUIRED_ARG_COUNT_OFFSET= ANNOTATION_OFFSET + 2;
/** /**
* The size in bytes of a PDOMCPPFunction record in the database. * The size in bytes of a PDOMCPPFunction record in the database.
*/ */
@SuppressWarnings("hiding") @SuppressWarnings("hiding")
protected static final int RECORD_SIZE = ANNOTATION + 1; protected static final int RECORD_SIZE = REQUIRED_ARG_COUNT_OFFSET + 4;
private static final short ANNOT_HAS_PACK = 0x100;
private ICPPFunctionType fType; private ICPPFunctionType fType;
private short fAnnotation= -1;
private int fRequiredArgCount= -1;
public PDOMCPPFunctionSpecialization(PDOMLinkage linkage, PDOMNode parent, ICPPFunction astFunction, PDOMBinding specialized) throws CoreException { public PDOMCPPFunctionSpecialization(PDOMLinkage linkage, PDOMNode parent, ICPPFunction astFunction, PDOMBinding specialized) throws CoreException {
super(linkage, parent, (ICPPSpecialization) astFunction, specialized); super(linkage, parent, (ICPPSpecialization) astFunction, specialized);
Database db = getDB(); Database db = getDB();
try { try {
IParameter[] astParams= astFunction.getParameters(); ICPPParameter[] astParams= astFunction.getParameters();
IFunctionType astFt= astFunction.getType(); IFunctionType astFt= astFunction.getType();
if (astFt != null) { if (astFt != null) {
getLinkage().storeType(record + FUNCTION_TYPE, astFt); getLinkage().storeType(record + FUNCTION_TYPE, astFt);
} }
ICPPFunction spAstFunc= (ICPPFunction) ((ICPPSpecialization)astFunction).getSpecializedBinding(); ICPPFunction origAstFunc= (ICPPFunction) ((ICPPSpecialization)astFunction).getSpecializedBinding();
ICPPParameter[] spAstParams= spAstFunc.getParameters(); ICPPParameter[] origAstParams= origAstFunc.getParameters();
if (origAstParams.length == 0) {
final int length= Math.min(spAstParams.length, astParams.length); db.putInt(record + NUM_PARAMS, 0);
db.putRecPtr(record + FIRST_PARAM, 0);
} else {
final int length= astParams.length;
db.putInt(record + NUM_PARAMS, length); db.putInt(record + NUM_PARAMS, length);
db.putRecPtr(record + FIRST_PARAM, 0); db.putRecPtr(record + FIRST_PARAM, 0);
PDOMCPPParameter origPar= null;
PDOMCPPParameterSpecialization next= null; PDOMCPPParameterSpecialization next= null;
for (int i= length-1; i >= 0; --i) { for (int i= length-1; i >= 0; --i) {
PDOMCPPParameter par= new PDOMCPPParameter(linkage, specialized, spAstParams[i], null); // There may be fewer or less original parameters, because of parameter packs.
next= new PDOMCPPParameterSpecialization(linkage, this, astParams[i], par, next); if (i < origAstParams.length-1) {
// Normal case
origPar= new PDOMCPPParameter(linkage, specialized, origAstParams[i], null);
} else if (origPar == null) {
// Use last parameter
origPar= new PDOMCPPParameter(linkage, specialized, origAstParams[origAstParams.length-1], null);
}
next= new PDOMCPPParameterSpecialization(linkage, this, astParams[i], origPar, next);
} }
db.putRecPtr(record + FIRST_PARAM, next == null ? 0 : next.getRecord()); db.putRecPtr(record + FIRST_PARAM, next == null ? 0 : next.getRecord());
db.putByte(record + ANNOTATION, PDOMCPPAnnotation.encodeAnnotation(astFunction)); }
fAnnotation = getAnnotation(astFunction);
db.putShort(record + ANNOTATION_OFFSET, fAnnotation);
db.putInt(record + REQUIRED_ARG_COUNT_OFFSET, astFunction.getRequiredArgumentCount());
} catch (DOMException e) { } catch (DOMException e) {
throw new CoreException(Util.createStatus(e)); throw new CoreException(Util.createStatus(e));
} }
@ -115,6 +135,14 @@ class PDOMCPPFunctionSpecialization extends PDOMCPPSpecialization implements ICP
} }
private short getAnnotation(ICPPFunction astFunction) throws DOMException {
int annot= PDOMCPPAnnotation.encodeAnnotation(astFunction);
if (astFunction.hasParameterPack()) {
annot |= ANNOT_HAS_PACK;
}
return (short) annot;
}
public PDOMCPPFunctionSpecialization(PDOMLinkage linkage, long bindingRecord) { public PDOMCPPFunctionSpecialization(PDOMLinkage linkage, long bindingRecord) {
super(linkage, bindingRecord); super(linkage, bindingRecord);
} }
@ -130,11 +158,22 @@ class PDOMCPPFunctionSpecialization extends PDOMCPPSpecialization implements ICP
} }
public boolean isInline() throws DOMException { public boolean isInline() throws DOMException {
return getBit(getByte(record + ANNOTATION), PDOMCAnnotation.INLINE_OFFSET); return getBit(readAnnotation(), PDOMCAnnotation.INLINE_OFFSET);
}
private short readAnnotation() {
if (fAnnotation == -1) {
try {
fAnnotation= getDB().getShort(record + ANNOTATION_OFFSET);
} catch (CoreException e) {
fAnnotation= 0;
}
}
return fAnnotation;
} }
public boolean isMutable() throws DOMException { public boolean isMutable() throws DOMException {
throw new PDOMNotImplementedError(); return false;
} }
public IScope getFunctionScope() throws DOMException { public IScope getFunctionScope() throws DOMException {
@ -182,11 +221,11 @@ class PDOMCPPFunctionSpecialization extends PDOMCPPSpecialization implements ICP
} }
public boolean isExtern() throws DOMException { public boolean isExtern() throws DOMException {
return getBit(getByte(record + ANNOTATION), PDOMCAnnotation.EXTERN_OFFSET); return getBit(readAnnotation(), PDOMCAnnotation.EXTERN_OFFSET);
} }
public boolean isExternC() throws DOMException { public boolean isExternC() throws DOMException {
return getBit(getByte(record + ANNOTATION), PDOMCPPAnnotation.EXTERN_C_OFFSET); return getBit(readAnnotation(), PDOMCPPAnnotation.EXTERN_C_OFFSET);
} }
public boolean isRegister() throws DOMException { public boolean isRegister() throws DOMException {
@ -195,11 +234,27 @@ class PDOMCPPFunctionSpecialization extends PDOMCPPSpecialization implements ICP
} }
public boolean isStatic() throws DOMException { public boolean isStatic() throws DOMException {
return getBit(getByte(record + ANNOTATION), PDOMCAnnotation.STATIC_OFFSET); return getBit(readAnnotation(), PDOMCAnnotation.STATIC_OFFSET);
} }
public boolean takesVarArgs() throws DOMException { public boolean takesVarArgs() throws DOMException {
return getBit(getByte(record + ANNOTATION), PDOMCAnnotation.VARARGS_OFFSET); return getBit(readAnnotation(), PDOMCAnnotation.VARARGS_OFFSET);
}
public int getRequiredArgumentCount() throws DOMException {
if (fRequiredArgCount == -1) {
try {
fRequiredArgCount= getDB().getInt(record + REQUIRED_ARG_COUNT_OFFSET);
} catch (CoreException e) {
fRequiredArgCount= 0;
}
}
return fRequiredArgCount;
}
public boolean hasParameterPack() {
return getBit(readAnnotation(), ANNOT_HAS_PACK);
} }
public boolean isConst() { public boolean isConst() {

View file

@ -70,6 +70,7 @@ import org.eclipse.cdt.internal.core.dom.parser.ITypeMarshalBuffer;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPArrayType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPArrayType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPBasicType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPBasicType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPFunctionType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPFunctionType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPParameterPackType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerToMemberType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPPointerType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType; import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPQualifierType;
@ -987,6 +988,8 @@ class PDOMCPPLinkage extends PDOMLinkage implements IIndexCPPBindingConstants {
return CPPPointerType.unmarshal(firstByte, buffer); return CPPPointerType.unmarshal(firstByte, buffer);
case ITypeMarshalBuffer.REFERENCE: case ITypeMarshalBuffer.REFERENCE:
return CPPReferenceType.unmarshal(firstByte, buffer); return CPPReferenceType.unmarshal(firstByte, buffer);
case ITypeMarshalBuffer.PACK_EXPANSION:
return CPPParameterPackType.unmarshal(firstByte, buffer);
case ITypeMarshalBuffer.POINTER_TO_MEMBER: case ITypeMarshalBuffer.POINTER_TO_MEMBER:
return CPPPointerToMemberType.unmarshal(firstByte, buffer); return CPPPointerToMemberType.unmarshal(firstByte, buffer);
} }

View file

@ -6,7 +6,7 @@
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* QNX - Initial API and implementation * Doug Schaefer (QNX) - Initial API and implementation
* IBM Corporation * IBM Corporation
* Andrew Ferguson (Symbian) * Andrew Ferguson (Symbian)
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
@ -37,8 +37,7 @@ import org.eclipse.cdt.internal.core.pdom.dom.c.PDOMCAnnotation;
import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.CoreException;
/** /**
* @author Doug Schaefer * Method
*
*/ */
class PDOMCPPMethod extends PDOMCPPFunction implements ICPPMethod { class PDOMCPPMethod extends PDOMCPPFunction implements ICPPMethod {
@ -137,7 +136,7 @@ class PDOMCPPMethod extends PDOMCPPFunction implements ICPPMethod {
} }
@Override @Override
public boolean isExtern() throws DOMException { public boolean isExtern() {
// ISO/IEC 14882:2003 9.2.6 // ISO/IEC 14882:2003 9.2.6
return false; return false;
} }
@ -148,13 +147,13 @@ class PDOMCPPMethod extends PDOMCPPFunction implements ICPPMethod {
} }
@Override @Override
public boolean isAuto() throws DOMException { public boolean isAuto() {
// ISO/IEC 14882:2003 9.2.6 // ISO/IEC 14882:2003 9.2.6
return false; return false;
} }
@Override @Override
public boolean isRegister() throws DOMException { public boolean isRegister() {
// ISO/IEC 14882:2003 9.2.6 // ISO/IEC 14882:2003 9.2.6
return false; return false;
} }

View file

@ -6,7 +6,7 @@
* http://www.eclipse.org/legal/epl-v10.html * http://www.eclipse.org/legal/epl-v10.html
* *
* Contributors: * Contributors:
* QNX - Initial API and implementation * Bryan Wilkinson (QNX) - Initial API and implementation
* Markus Schorn (Wind River Systems) * Markus Schorn (Wind River Systems)
*******************************************************************************/ *******************************************************************************/
package org.eclipse.cdt.internal.core.pdom.dom.cpp; package org.eclipse.cdt.internal.core.pdom.dom.cpp;
@ -27,8 +27,7 @@ import org.eclipse.cdt.internal.core.pdom.dom.c.PDOMCAnnotation;
import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.CoreException;
/** /**
* @author Bryan Wilkinson * Specialization of a method
*
*/ */
class PDOMCPPMethodSpecialization extends PDOMCPPFunctionSpecialization class PDOMCPPMethodSpecialization extends PDOMCPPFunctionSpecialization
implements ICPPMethod { implements ICPPMethod {
@ -111,7 +110,7 @@ class PDOMCPPMethodSpecialization extends PDOMCPPFunctionSpecialization
} }
public int getVisibility() throws DOMException { public int getVisibility() throws DOMException {
return PDOMCPPAnnotation.getVisibility(getByte(record + ANNOTATION)); return PDOMCPPAnnotation.getVisibility(getByte(record + ANNOTATION_OFFSET));
} }
@Override @Override

Some files were not shown because too many files have changed in this diff Show more