mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-04-29 19:45:01 +02:00
fix bug 90673
- template parameter as a target for resolving function references without parameters
This commit is contained in:
parent
1e5fda4a2c
commit
8468711bac
3 changed files with 62 additions and 46 deletions
|
@ -554,47 +554,6 @@ public class AST2CPPSpecFailingTest extends AST2SpecBaseTest {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
[--Start Example(CPP 14.3.2-5):
|
|
||||||
template<const int* pci> struct X { };
|
|
||||||
int ai[10];
|
|
||||||
X<ai> xi; // array to pointer and qualification conversions
|
|
||||||
struct Y { };
|
|
||||||
template<const Y& b> struct Z { };
|
|
||||||
Y y;
|
|
||||||
Z<y> z; // no conversion, but note extra cvqualification
|
|
||||||
template<int (&pa)[5]> struct W { };
|
|
||||||
int b[5];
|
|
||||||
W<b> w; // no conversion
|
|
||||||
void f(char);
|
|
||||||
void f(int);
|
|
||||||
template<void (*pf)(int)> struct A { };
|
|
||||||
A<&f> a; // selects f(int)
|
|
||||||
--End Example]
|
|
||||||
*/
|
|
||||||
public void test14_3_2s5() { // TODO raised bug 90673
|
|
||||||
StringBuffer buffer = new StringBuffer();
|
|
||||||
buffer.append("template<const int* pci> struct X { };\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("int ai[10];\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("X<ai> xi; // array to pointer and qualification conversions\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("struct Y { };\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("template<const Y& b> struct Z { };\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("Y y;\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("Z<y> z; // no conversion, but note extra cvqualification\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("template<int (&pa)[5]> struct W { };\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("int b[5];\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("W<b> w; // no conversion\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("void f(char);\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("void f(int);\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("template<void (*pf)(int)> struct A { };\n"); //$NON-NLS-1$
|
|
||||||
buffer.append("A<&f> a; // selects f(int)\n"); //$NON-NLS-1$
|
|
||||||
try {
|
|
||||||
parse(buffer.toString(), ParserLanguage.CPP, true, 0);
|
|
||||||
assertTrue(false);
|
|
||||||
} catch (Exception e) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
[--Start Example(CPP 14.5.3-1):
|
[--Start Example(CPP 14.5.3-1):
|
||||||
template<class T> class task;
|
template<class T> class task;
|
||||||
|
|
|
@ -11795,6 +11795,44 @@ public class AST2CPPSpecTest extends AST2SpecBaseTest {
|
||||||
parse(buffer.toString(), ParserLanguage.CPP, false, 0);
|
parse(buffer.toString(), ParserLanguage.CPP, false, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
[--Start Example(CPP 14.3.2-5):
|
||||||
|
template<const int* pci> struct X { };
|
||||||
|
int ai[10];
|
||||||
|
X<ai> xi; // array to pointer and qualification conversions
|
||||||
|
struct Y { };
|
||||||
|
template<const Y& b> struct Z { };
|
||||||
|
Y y;
|
||||||
|
Z<y> z; // no conversion, but note extra cvqualification
|
||||||
|
template<int (&pa)[5]> struct W { };
|
||||||
|
int b[5];
|
||||||
|
W<b> w; // no conversion
|
||||||
|
void f(char);
|
||||||
|
void f(int);
|
||||||
|
template<void (*pf)(int)> struct A { };
|
||||||
|
A<&f> a; // selects f(int)
|
||||||
|
--End Example]
|
||||||
|
*/
|
||||||
|
public void test14_3_2s5() throws Exception {
|
||||||
|
StringBuffer buffer = new StringBuffer();
|
||||||
|
buffer.append("template<const int* pci> struct X { };\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("int ai[10];\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("X<ai> xi; // array to pointer and qualification conversions\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("struct Y { };\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("template<const Y& b> struct Z { };\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("Y y;\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("Z<y> z; // no conversion, but note extra cvqualification\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("template<int (&pa)[5]> struct W { };\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("int b[5];\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("W<b> w; // no conversion\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("void f(char);\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("void f(int);\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("template<void (*pf)(int)> struct A { };\n"); //$NON-NLS-1$
|
||||||
|
buffer.append("A<&f> a; // selects f(int)\n"); //$NON-NLS-1$
|
||||||
|
|
||||||
|
parse(buffer.toString(), ParserLanguage.CPP, true, 0);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
[--Start Example(CPP 14.5.2-2):
|
[--Start Example(CPP 14.5.2-2):
|
||||||
template <class T> struct A {
|
template <class T> struct A {
|
||||||
|
|
|
@ -100,6 +100,8 @@ 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;
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPSpecialization;
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateDefinition;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateDefinition;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateNonTypeParameter;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateScope;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateScope;
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPUsingDeclaration;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPUsingDeclaration;
|
||||||
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
|
||||||
|
@ -2206,16 +2208,33 @@ public class CPPSemantics {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
//target is an explicit type conversion
|
//target is an explicit type conversion
|
||||||
// else if( prop == ICPPASTSimpleTypeConstructorExpression.INITIALIZER_VALUE )
|
|
||||||
// {
|
|
||||||
//
|
|
||||||
// }
|
|
||||||
//target is an explicit type conversion
|
|
||||||
else if( prop == IASTCastExpression.OPERAND )
|
else if( prop == IASTCastExpression.OPERAND )
|
||||||
{
|
{
|
||||||
IASTCastExpression cast = (IASTCastExpression) node.getParent();
|
IASTCastExpression cast = (IASTCastExpression) node.getParent();
|
||||||
return CPPVisitor.createType( cast.getTypeId().getAbstractDeclarator() );
|
return CPPVisitor.createType( cast.getTypeId().getAbstractDeclarator() );
|
||||||
}
|
}
|
||||||
|
//target is a template non-type parameter (14.3.2-5)
|
||||||
|
else if( prop == ICPPASTTemplateId.TEMPLATE_ID_ARGUMENT ){
|
||||||
|
ICPPASTTemplateId id = (ICPPASTTemplateId) node.getParent();
|
||||||
|
IASTNode [] args = id.getTemplateArguments();
|
||||||
|
int i = 0;
|
||||||
|
for ( ; i < args.length; i++ ) {
|
||||||
|
if( args[i] == node ){
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ICPPTemplateDefinition template = (ICPPTemplateDefinition) id.getTemplateName().resolveBinding();
|
||||||
|
if( template != null ){
|
||||||
|
try {
|
||||||
|
ICPPTemplateParameter [] ps = template.getTemplateParameters();
|
||||||
|
if( i < args.length && i < ps.length && ps[i] instanceof ICPPTemplateNonTypeParameter ){
|
||||||
|
return ((ICPPTemplateNonTypeParameter)ps[i]).getType();
|
||||||
|
}
|
||||||
|
} catch ( DOMException e ) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
//target is the return value of a function, operator or conversion
|
//target is the return value of a function, operator or conversion
|
||||||
else if( prop == IASTReturnStatement.RETURNVALUE )
|
else if( prop == IASTReturnStatement.RETURNVALUE )
|
||||||
{
|
{
|
||||||
|
|
Loading…
Add table
Reference in a new issue