mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-06-05 00:36:16 +02:00
- fixed up CompleteParseASTFactory.lookupQualifiedName in the case where the
tokenDuple has 1 segement - fixed CompleteParseASTFactory.createMethod to handle template ids - fixed instantiation of member templates - fixed up handling of explicit specializations
This commit is contained in:
parent
f0f5aa93c3
commit
63bc5b00d2
14 changed files with 246 additions and 178 deletions
|
@ -889,4 +889,38 @@ public class CompleteParseASTTemplateTest extends CompleteParseBaseTest {
|
||||||
assertReferenceTask( new Task( f2, 1, false, false ) );
|
assertReferenceTask( new Task( f2, 1, false, false ) );
|
||||||
assertReferenceTask( new Task( f3, 1, false, false ) );
|
assertReferenceTask( new Task( f3, 1, false, false ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void test_14_5_2__2_MemberFunctionTemplates() throws Exception{
|
||||||
|
Writer writer = new StringWriter();
|
||||||
|
writer.write("template < class T > struct A { ");
|
||||||
|
writer.write(" void f( int ); ");
|
||||||
|
writer.write(" template < class T2 > void f( T2 ); ");
|
||||||
|
writer.write("}; ");
|
||||||
|
|
||||||
|
writer.write("template <> void A<int>::f(int) {} //non-template member \n");
|
||||||
|
writer.write("template <> template<> void A<int>::f<>( int ) {} //template member \n");
|
||||||
|
|
||||||
|
writer.write("int main(){ ");
|
||||||
|
writer.write(" A< int > ac; ");
|
||||||
|
writer.write(" ac.f( 1 ); //non-template \n");
|
||||||
|
writer.write(" ac.f( 'c' ); //template \n");
|
||||||
|
writer.write(" ac.f<>(1); //template \n");
|
||||||
|
writer.write("} ");
|
||||||
|
|
||||||
|
Iterator i = parse( writer.toString() ).getDeclarations();
|
||||||
|
|
||||||
|
IASTTemplateDeclaration template = (IASTTemplateDeclaration) i.next();
|
||||||
|
IASTTemplateDeclaration spec1 = (IASTTemplateDeclaration) i.next();
|
||||||
|
IASTTemplateDeclaration spec2 = (IASTTemplateDeclaration) i.next();
|
||||||
|
|
||||||
|
IASTMethod f1 = (IASTMethod) spec1.getOwnedDeclaration();
|
||||||
|
IASTMethod f2 = (IASTMethod) spec2.getOwnedDeclaration();;
|
||||||
|
|
||||||
|
IASTFunction main = (IASTFunction) i.next();
|
||||||
|
assertFalse( i.hasNext() );
|
||||||
|
|
||||||
|
assertReferenceTask( new Task( f1, 1, false, false ) );
|
||||||
|
//we aren't going to be completely correct about references to explicit specializations
|
||||||
|
//due to limitations in the implementation, see bug 59811
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,78 +42,6 @@ public class FailingTemplateTests extends TestCase {
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* template < class T > struct A {
|
|
||||||
* void f( int );
|
|
||||||
* template < class T2 > void f( T2 );
|
|
||||||
* };
|
|
||||||
*
|
|
||||||
* template <> void A<int>::f(int) {} //non-template member
|
|
||||||
* template <> template<> void A<int>::f<>( int ) {} //template member
|
|
||||||
*
|
|
||||||
* int main(){
|
|
||||||
* A< char > ac;
|
|
||||||
* ac.f( 1 ); //non-template
|
|
||||||
* ac.f( 'c' ); //template
|
|
||||||
* ac.f<>(1); //template
|
|
||||||
* }
|
|
||||||
* @throws Exception
|
|
||||||
*/
|
|
||||||
public void test_14_5_2__2_MemberFunctionTemplates() throws Exception{
|
|
||||||
|
|
||||||
//This code snippet is misleading, the two definitions are actually
|
|
||||||
//explicit specializations for T = int, and so would not be used
|
|
||||||
//below or A< char >. This needs to be rewritten.
|
|
||||||
|
|
||||||
|
|
||||||
// newTable();
|
|
||||||
//
|
|
||||||
// ITemplateSymbol templateA = table.newTemplateSymbol( "A" );
|
|
||||||
// ISymbol T = table.newSymbol( "T", TypeInfo.t_templateParameter );
|
|
||||||
// templateA.addParameter( T );
|
|
||||||
//
|
|
||||||
// table.getCompilationUnit().addSymbol( templateA );
|
|
||||||
//
|
|
||||||
// IDerivableContainerSymbol A = table.newDerivableContainerSymbol( "A", TypeInfo.t_struct );
|
|
||||||
// templateA.addSymbol( A );
|
|
||||||
//
|
|
||||||
// IParameterizedSymbol f1 = table.newParameterizedSymbol("f", TypeInfo.t_function );
|
|
||||||
// f1.addParameter( TypeInfo.t_int, 0, null, false );
|
|
||||||
// f1.setIsForwardDeclaration( true );
|
|
||||||
// A.addSymbol( f1 );
|
|
||||||
//
|
|
||||||
// ITemplateSymbol templateF = table.newTemplateSymbol( "f" );
|
|
||||||
// ISymbol T2 = table.newSymbol( "T2", TypeInfo.t_templateParameter );
|
|
||||||
//
|
|
||||||
// IParameterizedSymbol f2 = table.newParameterizedSymbol( "f", TypeInfo.t_function );
|
|
||||||
// f2.addParameter( T2, null, false );
|
|
||||||
// f2.setIsForwardDeclaration( true );
|
|
||||||
// templateF.addSymbol( f2 );
|
|
||||||
//
|
|
||||||
// A.addSymbol( templateF );
|
|
||||||
//
|
|
||||||
// List args = new LinkedList();
|
|
||||||
// args.add( new TypeInfo( TypeInfo.t_int,0, null ) );
|
|
||||||
// ITemplateFactory factory = table.getCompilationUnit().lookupTemplateForMemberDefinition( "A", new LinkedList(), args );
|
|
||||||
//
|
|
||||||
// LinkedList params = new LinkedList();
|
|
||||||
// params.add( new TypeInfo( TypeInfo.t_int, 0, null ) );
|
|
||||||
// ISymbol look = factory.lookupMemberFunctionForDefinition( "f", params );
|
|
||||||
// assertEquals( look, f1 );
|
|
||||||
//
|
|
||||||
// IParameterizedSymbol f1Def = table.newParameterizedSymbol( "f", TypeInfo.t_function );
|
|
||||||
// f1Def.addParameter( TypeInfo.t_int, 0, null, false );
|
|
||||||
// look.setTypeSymbol( f1Def );
|
|
||||||
// factory.addSymbol( f1Def );
|
|
||||||
//
|
|
||||||
// factory = table.getCompilationUnit().lookupTemplateForMemberDefinition( "A", new LinkedList(), args );
|
|
||||||
// assertNotNull( factory );
|
|
||||||
//
|
|
||||||
// args.clear();
|
|
||||||
// args.add(table.newSymbol( ParserSymbolTable.EMPTY_NAME, TypeInfo.t_int ) );
|
|
||||||
// factory = factory.lookupTemplateForMemberDefinition( "f", new LinkedList(), new LinkedList(), args );
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A specialization of a member function template does not override a virtual
|
* A specialization of a member function template does not override a virtual
|
||||||
* function from a base class.
|
* function from a base class.
|
||||||
|
|
|
@ -1,3 +1,10 @@
|
||||||
|
2004-04-23 Andrew Niefer
|
||||||
|
- fixed up CompleteParseASTFactory.lookupQualifiedName in the case where the
|
||||||
|
tokenDuple has 1 segement
|
||||||
|
- fixed CompleteParseASTFactory.createMethod to handle template ids
|
||||||
|
- fixed instantiation of member templates
|
||||||
|
- fixed up handling of explicit specializations
|
||||||
|
|
||||||
2004-04-22 John Camelon
|
2004-04-22 John Camelon
|
||||||
Fixed https://bugs.eclipse.org/bugs/show_bug.cgi?id=47926
|
Fixed https://bugs.eclipse.org/bugs/show_bug.cgi?id=47926
|
||||||
|
|
||||||
|
|
|
@ -56,4 +56,6 @@ public interface ITokenDuple {
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
public abstract boolean syntaxOfName();
|
public abstract boolean syntaxOfName();
|
||||||
|
|
||||||
|
public String extractNameFromTemplateId();
|
||||||
}
|
}
|
|
@ -297,8 +297,10 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
else if( name == null ) return null;
|
else if( name == null ) return null;
|
||||||
|
|
||||||
List [] templateArgLists = name.getTemplateIdArgLists();
|
List [] templateArgLists = name.getTemplateIdArgLists();
|
||||||
|
List args = null;
|
||||||
int idx = 0;
|
int idx = 0;
|
||||||
switch( name.length() )
|
String image = null;
|
||||||
|
switch( name.getSegmentCount() )
|
||||||
{
|
{
|
||||||
case 0:
|
case 0:
|
||||||
if( throwOnError )
|
if( throwOnError )
|
||||||
|
@ -306,14 +308,21 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
else
|
else
|
||||||
return null;
|
return null;
|
||||||
case 1:
|
case 1:
|
||||||
firstSymbol = name.getFirstToken();
|
image = name.extractNameFromTemplateId();
|
||||||
result = lookupElement(startingScope, firstSymbol.getImage(), type, parameters, lookup );
|
args = ( templateArgLists != null ) ? getTemplateArgList( templateArgLists[ 0 ] ) : null;
|
||||||
|
result = lookupElement(startingScope, image, type, parameters, args, lookup );
|
||||||
|
|
||||||
if( result != null )
|
if( result != null )
|
||||||
{
|
{
|
||||||
if( lookup == LookupType.FORPARENTSCOPE && startingScope instanceof ITemplateFactory ){
|
if( lookup == LookupType.FORPARENTSCOPE && startingScope instanceof ITemplateFactory ){
|
||||||
((ITemplateFactory)startingScope).pushSymbol( result );
|
if( args != null )
|
||||||
|
((ITemplateFactory)startingScope).pushTemplateId( result, args );
|
||||||
|
else
|
||||||
|
((ITemplateFactory)startingScope).pushSymbol( result );
|
||||||
}
|
}
|
||||||
addReference( references, createReference( result, firstSymbol.getImage(), firstSymbol.getOffset() ));
|
addReference( references, createReference( result, image, name.getStartOffset() ));
|
||||||
|
if( args != null )
|
||||||
|
addTemplateIdReferences( references, templateArgLists[0] );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -328,7 +337,7 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( throwOnError )
|
if ( throwOnError )
|
||||||
handleProblem( IProblem.SEMANTIC_NAME_NOT_FOUND, firstSymbol.getImage(), -1, -1, firstSymbol.getLineNumber() );
|
handleProblem( IProblem.SEMANTIC_NAME_NOT_FOUND, image, -1, -1, name.getLineNumber() );
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -348,7 +357,7 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
}
|
}
|
||||||
if( t.isPointer() ) break;
|
if( t.isPointer() ) break;
|
||||||
|
|
||||||
String image = t.getImage();
|
image = t.getImage();
|
||||||
int offset = t.getOffset();
|
int offset = t.getOffset();
|
||||||
|
|
||||||
if( templateArgLists != null && templateArgLists[ idx ] != null ){
|
if( templateArgLists != null && templateArgLists[ idx ] != null ){
|
||||||
|
@ -361,22 +370,19 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
if( result instanceof IDeferredTemplateInstance ){
|
if( result instanceof IDeferredTemplateInstance ){
|
||||||
result = ((IDeferredTemplateInstance)result).getTemplate().getTemplatedSymbol();
|
result = ((IDeferredTemplateInstance)result).getTemplate().getTemplatedSymbol();
|
||||||
}
|
}
|
||||||
|
args = ( templateArgLists != null ) ? getTemplateArgList( templateArgLists[ idx ] ) : null;
|
||||||
if( t == name.getLastToken() )
|
if( t == name.getLastToken() )
|
||||||
if( templateArgLists != null )
|
result = lookupElement((IContainerSymbol)result, image, type, parameters, args, ( lookup == LookupType.FORDEFINITION ) ? lookup : LookupType.QUALIFIED );
|
||||||
result = lookupElement((IContainerSymbol)result, image, type, parameters, getTemplateArgList( templateArgLists[idx] ), ( lookup == LookupType.FORDEFINITION ) ? lookup : LookupType.QUALIFIED );
|
|
||||||
else
|
|
||||||
result = lookupElement((IContainerSymbol)result, image, type, parameters, ( lookup == LookupType.FORDEFINITION ) ? lookup : LookupType.QUALIFIED );
|
|
||||||
else
|
else
|
||||||
if( templateArgLists != null && templateArgLists[idx] != null )
|
if( templateArgLists != null && templateArgLists[idx] != null )
|
||||||
result = ((IContainerSymbol)result).lookupTemplateId( image, getTemplateArgList( templateArgLists[idx] ) );
|
result = ((IContainerSymbol)result).lookupTemplateId( image, args );
|
||||||
else
|
else
|
||||||
result = ((IContainerSymbol)result).lookupNestedNameSpecifier( image );
|
result = ((IContainerSymbol)result).lookupNestedNameSpecifier( image );
|
||||||
|
|
||||||
if( result != null ){
|
if( result != null ){
|
||||||
if( lookup == LookupType.FORPARENTSCOPE && startingScope instanceof ITemplateFactory ){
|
if( lookup == LookupType.FORPARENTSCOPE && startingScope instanceof ITemplateFactory ){
|
||||||
if( templateArgLists != null && templateArgLists[idx] != null )
|
if( templateArgLists != null && templateArgLists[idx] != null )
|
||||||
((ITemplateFactory)startingScope).pushTemplateId( result, getTemplateArgList( templateArgLists[idx] ) );
|
((ITemplateFactory)startingScope).pushTemplateId( result, args );
|
||||||
else
|
else
|
||||||
((ITemplateFactory)startingScope).pushSymbol( result );
|
((ITemplateFactory)startingScope).pushSymbol( result );
|
||||||
}
|
}
|
||||||
|
@ -2269,7 +2275,17 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
nameDuple = nameDuple.getLastSegment();
|
nameDuple = nameDuple.getLastSegment();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
symbol = pst.newParameterizedSymbol( nameDuple.toString(), TypeInfo.t_function );
|
String methodName = null;
|
||||||
|
List templateIdArgList = null;
|
||||||
|
//template-id?
|
||||||
|
if( nameDuple.getTemplateIdArgLists() != null ){
|
||||||
|
templateIdArgList = nameDuple.getTemplateIdArgLists()[ 0 ];
|
||||||
|
methodName = nameDuple.extractNameFromTemplateId();
|
||||||
|
} else {
|
||||||
|
methodName = nameDuple.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
symbol = pst.newParameterizedSymbol( methodName, TypeInfo.t_function );
|
||||||
setFunctionTypeInfoBits(isInline, isFriend, isStatic, symbol);
|
setFunctionTypeInfoBits(isInline, isFriend, isStatic, symbol);
|
||||||
setMethodTypeInfoBits( symbol, isConst, isVolatile, isVirtual, isExplicit );
|
setMethodTypeInfoBits( symbol, isConst, isVolatile, isVirtual, isExplicit );
|
||||||
symbol.setHasVariableArgs( hasVariableArguments );
|
symbol.setHasVariableArgs( hasVariableArguments );
|
||||||
|
@ -2291,9 +2307,9 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
if(parentName.indexOf(DOUBLE_COLON) != -1){
|
if(parentName.indexOf(DOUBLE_COLON) != -1){
|
||||||
parentName = parentName.substring(parentName.lastIndexOf(DOUBLE_COLON) + DOUBLE_COLON.length());
|
parentName = parentName.substring(parentName.lastIndexOf(DOUBLE_COLON) + DOUBLE_COLON.length());
|
||||||
}
|
}
|
||||||
if( parentName.equals(nameDuple.toString()) ){
|
if( parentName.equals(methodName) ){
|
||||||
isConstructor = true;
|
isConstructor = true;
|
||||||
} else if(nameDuple.getFirstToken().getType() == IToken.tCOMPL && parentName.equals(nameDuple.getLastToken().getImage())){
|
} else if(methodName.equals( "~" + parentName )){ //$NON-NLS-1$
|
||||||
isDestructor = true;
|
isDestructor = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2318,14 +2334,10 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
|
|
||||||
List functionReferences = new ArrayList();
|
List functionReferences = new ArrayList();
|
||||||
|
|
||||||
if( isFriend )
|
functionDeclaration = (IParameterizedSymbol) lookupQualifiedName( ownerScope, nameDuple,
|
||||||
{
|
isConstructor ? TypeInfo.t_constructor : TypeInfo.t_function,
|
||||||
functionDeclaration =
|
functionParameters, functionReferences, false,
|
||||||
(IParameterizedSymbol) lookupQualifiedName(ownerScope, nameDuple, isConstructor ? TypeInfo.t_constructor : TypeInfo.t_function, functionParameters, functionReferences, false, LookupType.FORFRIENDSHIP );
|
isFriend ? LookupType.FORFRIENDSHIP : LookupType.FORDEFINITION );
|
||||||
} else {
|
|
||||||
functionDeclaration =
|
|
||||||
(IParameterizedSymbol) lookupQualifiedName(ownerScope, nameDuple.toString(), isConstructor ? TypeInfo.t_constructor : TypeInfo.t_function, functionParameters, 0, functionReferences, false, LookupType.FORDEFINITION );
|
|
||||||
}
|
|
||||||
|
|
||||||
previouslyDeclared = ( functionDeclaration != null ) && functionDeclaration.isType( isConstructor ? TypeInfo.t_constructor : TypeInfo.t_function );
|
previouslyDeclared = ( functionDeclaration != null ) && functionDeclaration.isType( isConstructor ? TypeInfo.t_constructor : TypeInfo.t_function );
|
||||||
|
|
||||||
|
@ -2361,8 +2373,12 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
((IDerivableContainerSymbol)ownerScope).addFriend( functionDeclaration );
|
((IDerivableContainerSymbol)ownerScope).addFriend( functionDeclaration );
|
||||||
else
|
else
|
||||||
((IDerivableContainerSymbol)ownerScope).addFriend( symbol );
|
((IDerivableContainerSymbol)ownerScope).addFriend( symbol );
|
||||||
} else if( !isConstructor )
|
} else if( !isConstructor ){
|
||||||
ownerScope.addSymbol( symbol );
|
if( templateIdArgList == null )
|
||||||
|
ownerScope.addSymbol( symbol );
|
||||||
|
else
|
||||||
|
ownerScope.addTemplateId( symbol, getTemplateArgList( templateIdArgList ) );
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
symbol.setType( TypeInfo.t_constructor );
|
symbol.setType( TypeInfo.t_constructor );
|
||||||
|
@ -2380,6 +2396,9 @@ public class CompleteParseASTFactory extends BaseASTFactory implements IASTFacto
|
||||||
attachSymbolExtension( symbol, method, isFunctionDefinition );
|
attachSymbolExtension( symbol, method, isFunctionDefinition );
|
||||||
return method;
|
return method;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param symbol
|
* @param symbol
|
||||||
* @param constructorChain
|
* @param constructorChain
|
||||||
|
|
|
@ -99,14 +99,21 @@ public class ContainerSymbol extends BasicSymbol implements IContainerSymbol {
|
||||||
|
|
||||||
if( !template.getExplicitSpecializations().isEmpty() ){
|
if( !template.getExplicitSpecializations().isEmpty() ){
|
||||||
List argList = new LinkedList();
|
List argList = new LinkedList();
|
||||||
|
boolean hasAllParams = true;
|
||||||
Iterator templateParams = template.getParameterList().iterator();
|
Iterator templateParams = template.getParameterList().iterator();
|
||||||
while( templateParams.hasNext() ){
|
while( templateParams.hasNext() ){
|
||||||
argList.add( argMap.get( templateParams.next() ) );
|
Object obj = argMap.get( templateParams.next() );
|
||||||
|
if( obj == null ){
|
||||||
|
hasAllParams = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
argList.add( obj );
|
||||||
|
}
|
||||||
|
if( hasAllParams){
|
||||||
|
ISymbol temp = TemplateEngine.checkForTemplateExplicitSpecialization( template, symbol, argList );
|
||||||
|
if( temp != null )
|
||||||
|
containedSymbol = temp;
|
||||||
}
|
}
|
||||||
|
|
||||||
ISymbol temp = TemplateEngine.checkForTemplateExplicitSpecialization( template, symbol, argList );
|
|
||||||
if( temp != null )
|
|
||||||
containedSymbol = temp;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Map instanceMap = argMap;
|
Map instanceMap = argMap;
|
||||||
|
@ -797,49 +804,6 @@ public class ContainerSymbol extends BasicSymbol implements IContainerSymbol {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// public ITemplateFactory lookupTemplateForMemberDefinition( String name, List parameters, List arguments ) throws ParserSymbolTableException{
|
|
||||||
// LookupData data = new LookupData( name, TypeInfo.t_any );
|
|
||||||
//
|
|
||||||
// ParserSymbolTable.lookup( data, this );
|
|
||||||
//
|
|
||||||
// Object look = null;
|
|
||||||
// try{
|
|
||||||
// look = ParserSymbolTable.resolveAmbiguities( data );
|
|
||||||
// } catch ( ParserSymbolTableException e ){
|
|
||||||
// if( e.reason != ParserSymbolTableException.r_UnableToResolveFunction ){
|
|
||||||
// throw e;
|
|
||||||
// }
|
|
||||||
// if( !data.foundItems.isEmpty() ){
|
|
||||||
// look = data.foundItems.get( name );
|
|
||||||
// if(!( look instanceof List ) ){
|
|
||||||
// throw new ParserSymbolTableError();
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// ITemplateSymbol template = (ITemplateSymbol) (( look instanceof ITemplateSymbol ) ? look : null);
|
|
||||||
// if( template == null ){
|
|
||||||
// if( look instanceof ISymbol ){
|
|
||||||
// ISymbol symbol = (ISymbol) look;
|
|
||||||
// if( symbol.isTemplateMember() && symbol.getContainingSymbol().isType( TypeInfo.t_template ) ){
|
|
||||||
// template = (ITemplateSymbol) symbol.getContainingSymbol();
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// }
|
|
||||||
// if( template != null ){
|
|
||||||
// template = TemplateEngine.selectTemplateOrSpecialization( template, parameters, arguments );
|
|
||||||
// if( template != null ){
|
|
||||||
// return new TemplateFactory( template, parameters, arguments );
|
|
||||||
// }
|
|
||||||
// } else if ( look instanceof List ){
|
|
||||||
// return new TemplateFactory( new HashSet( (List)look ), parameters, arguments );
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// return null;
|
|
||||||
// }
|
|
||||||
|
|
||||||
|
|
||||||
public List prefixLookup( TypeFilter filter, String prefix, boolean qualified ) throws ParserSymbolTableException{
|
public List prefixLookup( TypeFilter filter, String prefix, boolean qualified ) throws ParserSymbolTableException{
|
||||||
LookupData data = new LookupData( prefix, filter );
|
LookupData data = new LookupData( prefix, filter );
|
||||||
data.qualified = qualified;
|
data.qualified = qualified;
|
||||||
|
|
|
@ -42,6 +42,7 @@ public interface ITemplateSymbol extends IParameterizedSymbol {
|
||||||
public List findArgumentsFor( IContainerSymbol instance );
|
public List findArgumentsFor( IContainerSymbol instance );
|
||||||
|
|
||||||
public void addInstantiation( IContainerSymbol instance, List args );
|
public void addInstantiation( IContainerSymbol instance, List args );
|
||||||
|
public void removeInstantiation( IContainerSymbol symbol );
|
||||||
|
|
||||||
public void addExplicitSpecialization( ISymbol symbol, List args ) throws ParserSymbolTableException;
|
public void addExplicitSpecialization( ISymbol symbol, List args ) throws ParserSymbolTableException;
|
||||||
|
|
||||||
|
@ -77,8 +78,4 @@ public interface ITemplateSymbol extends IParameterizedSymbol {
|
||||||
public static final DeferredKind PARENT = new DeferredKind( 2 );
|
public static final DeferredKind PARENT = new DeferredKind( 2 );
|
||||||
public static final DeferredKind TYPE_SYMBOL = new DeferredKind( 3 );
|
public static final DeferredKind TYPE_SYMBOL = new DeferredKind( 3 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -80,21 +80,24 @@ public class ParameterizedSymbol extends ContainerSymbol implements IParameteriz
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Iterator iter = getParameterList().iterator();
|
//handle template parameter lists in TemplateSymbol, only do function parameter lists here.
|
||||||
|
if( !isType( TypeInfo.t_template ) ){
|
||||||
newParameterized.getParameterList().clear();
|
Iterator iter = getParameterList().iterator();
|
||||||
newParameterized.getParameterMap().clear();
|
|
||||||
|
|
||||||
ISymbol param = null, newParam = null;
|
|
||||||
|
|
||||||
while( iter.hasNext() ){
|
|
||||||
param = (ISymbol) iter.next();
|
|
||||||
newParam = param.instantiate( template, argMap );
|
|
||||||
|
|
||||||
newParameterized.getParameterList().add( newParam );
|
newParameterized.getParameterList().clear();
|
||||||
if( !newParam.getName().equals( ParserSymbolTable.EMPTY_NAME ) ){
|
newParameterized.getParameterMap().clear();
|
||||||
newParameterized.getParameterMap().put( newParam.getName(), newParam );
|
|
||||||
}
|
ISymbol param = null, newParam = null;
|
||||||
|
|
||||||
|
while( iter.hasNext() ){
|
||||||
|
param = (ISymbol) iter.next();
|
||||||
|
newParam = param.instantiate( template, argMap );
|
||||||
|
|
||||||
|
newParameterized.getParameterList().add( newParam );
|
||||||
|
if( !newParam.getName().equals( ParserSymbolTable.EMPTY_NAME ) ){
|
||||||
|
newParameterized.getParameterMap().put( newParam.getName(), newParam );
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return newParameterized;
|
return newParameterized;
|
||||||
|
|
|
@ -565,7 +565,7 @@ public class ParserSymbolTable {
|
||||||
}
|
}
|
||||||
|
|
||||||
if( numTemplateFunctions > 0 ){
|
if( numTemplateFunctions > 0 ){
|
||||||
if( data.parameters != null && !data.exactFunctionsOnly ){
|
if( data.parameters != null && ( !data.exactFunctionsOnly || data.templateParameters != null ) ){
|
||||||
List fns = TemplateEngine.selectTemplateFunctions( templateFunctionSet, data.parameters, data.templateParameters );
|
List fns = TemplateEngine.selectTemplateFunctions( templateFunctionSet, data.parameters, data.templateParameters );
|
||||||
functionSet.addAll( fns );
|
functionSet.addAll( fns );
|
||||||
numFunctions = functionSet.size();
|
numFunctions = functionSet.size();
|
||||||
|
@ -984,7 +984,7 @@ public class ParserSymbolTable {
|
||||||
|
|
||||||
reduceToViable( data, functions );
|
reduceToViable( data, functions );
|
||||||
|
|
||||||
if( data.exactFunctionsOnly ){
|
if( data.exactFunctionsOnly && data.templateParameters == null ){
|
||||||
if( functions.size() == 1 ){
|
if( functions.size() == 1 ){
|
||||||
return (IParameterizedSymbol) functions.get( 0 );
|
return (IParameterizedSymbol) functions.get( 0 );
|
||||||
} else if( functions.size() == 0 ){
|
} else if( functions.size() == 0 ){
|
||||||
|
@ -1153,7 +1153,10 @@ public class ParserSymbolTable {
|
||||||
if( !hasWorse ){
|
if( !hasWorse ){
|
||||||
if( !hasBetter ){
|
if( !hasBetter ){
|
||||||
//if they are both template functions, we can order them that way
|
//if they are both template functions, we can order them that way
|
||||||
if( bestFn.isTemplateInstance() && currFn.isTemplateInstance() ){
|
boolean bestIsTemplate = bestFn.getContainingSymbol() instanceof ITemplateSymbol;
|
||||||
|
boolean currIsTemplate = currFn.getContainingSymbol() instanceof ITemplateSymbol;
|
||||||
|
if( bestIsTemplate && currIsTemplate )
|
||||||
|
{
|
||||||
ITemplateSymbol t1 = (ITemplateSymbol) bestFn.getInstantiatedSymbol().getContainingSymbol();
|
ITemplateSymbol t1 = (ITemplateSymbol) bestFn.getInstantiatedSymbol().getContainingSymbol();
|
||||||
ITemplateSymbol t2 = (ITemplateSymbol) currFn.getInstantiatedSymbol().getContainingSymbol();
|
ITemplateSymbol t2 = (ITemplateSymbol) currFn.getInstantiatedSymbol().getContainingSymbol();
|
||||||
int order = TemplateEngine.orderTemplateFunctions( t1, t2 );
|
int order = TemplateEngine.orderTemplateFunctions( t1, t2 );
|
||||||
|
@ -1163,13 +1166,13 @@ public class ParserSymbolTable {
|
||||||
ambiguous = false;
|
ambiguous = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//we prefer normal functions over template functions, unless the specified template arguments
|
//we prefer normal functions over template functions, unless we specified template arguments
|
||||||
else if( bestFn.isTemplateInstance() && !currFn.isTemplateInstance() ){
|
else if( bestIsTemplate && !currIsTemplate ){
|
||||||
if( data.templateParameters == null )
|
if( data.templateParameters == null )
|
||||||
hasBetter = true;
|
hasBetter = true;
|
||||||
else
|
else
|
||||||
ambiguous = false;
|
ambiguous = false;
|
||||||
} else if( !bestFn.isTemplateInstance() && currFn.isTemplateInstance() ){
|
} else if( !bestIsTemplate && currIsTemplate ){
|
||||||
if( data.templateParameters == null )
|
if( data.templateParameters == null )
|
||||||
ambiguous = false;
|
ambiguous = false;
|
||||||
else
|
else
|
||||||
|
|
|
@ -1297,8 +1297,8 @@ public final class TemplateEngine {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
ITemplateSymbol t1 = (ITemplateSymbol) getContainingTemplate( p1 );//.getContainingSymbol();
|
ITemplateSymbol t1 = getContainingTemplate( p1 );
|
||||||
ITemplateSymbol t2 = (ITemplateSymbol) getContainingTemplate( p2 );//.getContainingSymbol();
|
ITemplateSymbol t2 = getContainingTemplate( p2 );
|
||||||
|
|
||||||
if( p1.getTypeInfo().getTemplateParameterType() == TypeInfo.t_typeName )
|
if( p1.getTypeInfo().getTemplateParameterType() == TypeInfo.t_typeName )
|
||||||
{
|
{
|
||||||
|
|
|
@ -57,7 +57,8 @@ public class TemplateFactory extends ExtensibleSymbol implements ITemplateFactor
|
||||||
*/
|
*/
|
||||||
public void addTemplateId(ISymbol symbol, List args) throws ParserSymbolTableException {
|
public void addTemplateId(ISymbol symbol, List args) throws ParserSymbolTableException {
|
||||||
ISymbol previous = findPreviousSymbol( symbol, args );
|
ISymbol previous = findPreviousSymbol( symbol, args );
|
||||||
ITemplateSymbol origTemplate = (previous != null ) ? (ITemplateSymbol) previous.getContainingSymbol() : null;
|
ITemplateSymbol origTemplate = (previous != null && previous.getContainingSymbol() instanceof ITemplateSymbol )
|
||||||
|
? (ITemplateSymbol) previous.getContainingSymbol() : null;
|
||||||
|
|
||||||
if( origTemplate == null ){
|
if( origTemplate == null ){
|
||||||
throw new ParserSymbolTableException( ParserSymbolTableException.r_BadTemplate );
|
throw new ParserSymbolTableException( ParserSymbolTableException.r_BadTemplate );
|
||||||
|
@ -131,7 +132,6 @@ public class TemplateFactory extends ExtensibleSymbol implements ITemplateFactor
|
||||||
int numSymbols = symbols.size();
|
int numSymbols = symbols.size();
|
||||||
|
|
||||||
if( templateParamState ){
|
if( templateParamState ){
|
||||||
ITemplateSymbol template = (ITemplateSymbol) container.getContainingSymbol();
|
|
||||||
List args = (List) argMap.get( container );
|
List args = (List) argMap.get( container );
|
||||||
addExplicitSpecialization( (ITemplateSymbol) container.getContainingSymbol(), symbol, args );
|
addExplicitSpecialization( (ITemplateSymbol) container.getContainingSymbol(), symbol, args );
|
||||||
return;
|
return;
|
||||||
|
@ -311,6 +311,19 @@ public class TemplateFactory extends ExtensibleSymbol implements ITemplateFactor
|
||||||
private void addExplicitSpecialization( ITemplateSymbol template, ISymbol symbol, List arguments ) throws ParserSymbolTableException {
|
private void addExplicitSpecialization( ITemplateSymbol template, ISymbol symbol, List arguments ) throws ParserSymbolTableException {
|
||||||
template.addExplicitSpecialization( symbol, arguments );
|
template.addExplicitSpecialization( symbol, arguments );
|
||||||
|
|
||||||
|
Iterator i = symbols.iterator();
|
||||||
|
while( i.hasNext() ){
|
||||||
|
IContainerSymbol sym = (IContainerSymbol) i.next();
|
||||||
|
ISymbol instantiated = sym.getInstantiatedSymbol();
|
||||||
|
if( instantiated != null ){
|
||||||
|
IContainerSymbol container = instantiated.getContainingSymbol();
|
||||||
|
if( container.isType( TypeInfo.t_template ) ){
|
||||||
|
((ITemplateSymbol) container ).removeInstantiation( sym );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
if( getASTExtension() != null ){
|
if( getASTExtension() != null ){
|
||||||
ASTTemplateSpecialization spec = (ASTTemplateSpecialization) getASTExtension().getPrimaryDeclaration();
|
ASTTemplateSpecialization spec = (ASTTemplateSpecialization) getASTExtension().getPrimaryDeclaration();
|
||||||
spec.setOwnedDeclaration( symbol );
|
spec.setOwnedDeclaration( symbol );
|
||||||
|
@ -527,7 +540,7 @@ public class TemplateFactory extends ExtensibleSymbol implements ITemplateFactor
|
||||||
|
|
||||||
if( look instanceof ITemplateSymbol ){
|
if( look instanceof ITemplateSymbol ){
|
||||||
ITemplateSymbol t = TemplateEngine.selectTemplateOrSpecialization( (ITemplateSymbol) look, getNextAvailableTemplate().getParameterList(), arguments );
|
ITemplateSymbol t = TemplateEngine.selectTemplateOrSpecialization( (ITemplateSymbol) look, getNextAvailableTemplate().getParameterList(), arguments );
|
||||||
look = ((ITemplateSymbol) look).getTemplatedSymbol();
|
look = t.getTemplatedSymbol();
|
||||||
}
|
}
|
||||||
return (IContainerSymbol) (( look instanceof IContainerSymbol) ? look : null);
|
return (IContainerSymbol) (( look instanceof IContainerSymbol) ? look : null);
|
||||||
}
|
}
|
||||||
|
|
|
@ -162,6 +162,26 @@ public class TemplateSymbol extends ParameterizedSymbol implements ITemplateSymb
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public ISymbol instantiate( ITemplateSymbol template, Map argMap ) throws ParserSymbolTableException{
|
||||||
|
if( !isTemplateMember() ){
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
TemplateSymbol newTemplate = (TemplateSymbol) super.instantiate( template, argMap );
|
||||||
|
|
||||||
|
//we don't want to instantiate the template parameters, just the defaults if there are any
|
||||||
|
Iterator iter = newTemplate.getParameterList().iterator();
|
||||||
|
ISymbol param = null;
|
||||||
|
while( iter.hasNext() ){
|
||||||
|
param = (ISymbol) iter.next();
|
||||||
|
Object obj = param.getTypeInfo().getDefault();
|
||||||
|
if( obj instanceof TypeInfo ){
|
||||||
|
param.getTypeInfo().setDefault( TemplateEngine.instantiateTypeInfo( (TypeInfo) obj, template, argMap ) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return newTemplate;
|
||||||
|
}
|
||||||
|
|
||||||
public void addParameter( ISymbol param ) {
|
public void addParameter( ISymbol param ) {
|
||||||
throw new ParserSymbolTableError( ParserSymbolTableError.r_OperationNotSupported );
|
throw new ParserSymbolTableError( ParserSymbolTableError.r_OperationNotSupported );
|
||||||
|
@ -278,11 +298,24 @@ public class TemplateSymbol extends ParameterizedSymbol implements ITemplateSymb
|
||||||
if( found == null && getTemplatedSymbol().getName().equals( symbol.getName() ) ){
|
if( found == null && getTemplatedSymbol().getName().equals( symbol.getName() ) ){
|
||||||
found = getTemplatedSymbol();
|
found = getTemplatedSymbol();
|
||||||
|
|
||||||
IContainerSymbol instance = findInstantiation( args );
|
IContainerSymbol instance = findInstantiation( actualArgs );
|
||||||
if( instance != null ){
|
if( instance != null ){
|
||||||
_instantiations.remove( findArgumentsFor( instance ) );
|
_instantiations.remove( findArgumentsFor( instance ) );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if( found != null && found.getTypeInfo().isForwardDeclaration() && found.getTypeSymbol() == symbol ){
|
||||||
|
//in defining the explicit specialization for a member function, the factory would have set
|
||||||
|
//the specialization as the definition of the original declaration, which it is not
|
||||||
|
found.setTypeSymbol( null );
|
||||||
|
}
|
||||||
|
|
||||||
|
//TODO, once we can instantiate members as we need them instead of at the same time as the class
|
||||||
|
//then found should stay as the instance, for now though, we need the original (not 100% correct
|
||||||
|
//but the best we can do for now)
|
||||||
|
while( found.isTemplateInstance() ){
|
||||||
|
found = found.getInstantiatedSymbol();
|
||||||
|
}
|
||||||
|
|
||||||
if( found != null ){
|
if( found != null ){
|
||||||
symbol.setIsTemplateMember( true );
|
symbol.setIsTemplateMember( true );
|
||||||
|
@ -357,6 +390,13 @@ public class TemplateSymbol extends ParameterizedSymbol implements ITemplateSymb
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void removeInstantiation( IContainerSymbol symbol ){
|
||||||
|
List args = findArgumentsFor( symbol );
|
||||||
|
if( args != null ){
|
||||||
|
_instantiations.remove( args );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public Map getDefinitionParameterMap(){
|
public Map getDefinitionParameterMap(){
|
||||||
if( _defnParameterMap == null ){
|
if( _defnParameterMap == null ){
|
||||||
_defnParameterMap = new HashMap();
|
_defnParameterMap = new HashMap();
|
||||||
|
|
|
@ -229,6 +229,7 @@ public class TypeInfo {
|
||||||
"enum", //$NON-NLS-1$ t_enumeration
|
"enum", //$NON-NLS-1$ t_enumeration
|
||||||
"", //$NON-NLS-1$ t_constructor
|
"", //$NON-NLS-1$ t_constructor
|
||||||
"", //$NON-NLS-1$ t_function
|
"", //$NON-NLS-1$ t_function
|
||||||
|
"_Bool", //$NON-NLS-1$ t__Bool
|
||||||
"bool", //$NON-NLS-1$ t_bool
|
"bool", //$NON-NLS-1$ t_bool
|
||||||
"char", //$NON-NLS-1$ t_char
|
"char", //$NON-NLS-1$ t_char
|
||||||
"wchar_t", //$NON-NLS-1$ t_wchar_t
|
"wchar_t", //$NON-NLS-1$ t_wchar_t
|
||||||
|
@ -240,7 +241,9 @@ public class TypeInfo {
|
||||||
"", //$NON-NLS-1$ t_block
|
"", //$NON-NLS-1$ t_block
|
||||||
"template", //$NON-NLS-1$ t_template
|
"template", //$NON-NLS-1$ t_template
|
||||||
"", //$NON-NLS-1$ t_asm
|
"", //$NON-NLS-1$ t_asm
|
||||||
"" //$NON-NLS-1$ t_linkage
|
"", //$NON-NLS-1$ t_linkage
|
||||||
|
"", //$NON-NLS-1$ t_templateParameter
|
||||||
|
"typename" //$NON-NLS-1$ t_typeName
|
||||||
};
|
};
|
||||||
//Partial ordering :
|
//Partial ordering :
|
||||||
// none < const
|
// none < const
|
||||||
|
|
|
@ -437,4 +437,59 @@ public class TokenDuple implements ITokenDuple {
|
||||||
return true;
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String extractNameFromTemplateId(){
|
||||||
|
ITokenDuple nameDuple = getLastSegment();
|
||||||
|
|
||||||
|
Iterator i = nameDuple.iterator();
|
||||||
|
|
||||||
|
if( !i.hasNext() )
|
||||||
|
return "";//$NON-NLS-1$
|
||||||
|
|
||||||
|
StringBuffer nameBuffer = new StringBuffer();
|
||||||
|
IToken token = (IToken) i.next();
|
||||||
|
nameBuffer.append( token.getImage() );
|
||||||
|
|
||||||
|
if( !i.hasNext() )
|
||||||
|
return nameBuffer.toString();
|
||||||
|
|
||||||
|
//appending of spaces needs to be the same as in toString()
|
||||||
|
|
||||||
|
//destructors
|
||||||
|
if( token.getType() == IToken.tCOMPL ){
|
||||||
|
token = (IToken) i.next();
|
||||||
|
nameBuffer.append( token.getImage() );
|
||||||
|
}
|
||||||
|
//operators
|
||||||
|
else if( token.getType() == IToken.t_operator ){
|
||||||
|
token = (IToken) i.next();
|
||||||
|
nameBuffer.append( ' ' );
|
||||||
|
nameBuffer.append( token.getImage() );
|
||||||
|
|
||||||
|
if( !i.hasNext() )
|
||||||
|
return nameBuffer.toString();
|
||||||
|
|
||||||
|
//operator new [] and operator delete []
|
||||||
|
if( (token.getType() == IToken.t_new || token.getType() == IToken.t_delete) &&
|
||||||
|
(token.getNext().getType() == IToken.tLBRACKET ) )
|
||||||
|
{
|
||||||
|
nameBuffer.append( ' ' );
|
||||||
|
nameBuffer.append( ((IToken)i.next()).getImage() );
|
||||||
|
nameBuffer.append( ((IToken)i.next()).getImage() );
|
||||||
|
}
|
||||||
|
//operator []
|
||||||
|
else if( token.getType() == IToken.tLBRACKET )
|
||||||
|
{
|
||||||
|
nameBuffer.append( ((IToken)i.next()).getImage() );
|
||||||
|
}
|
||||||
|
//operator ( )
|
||||||
|
else if( token.getType() == IToken.tLBRACE )
|
||||||
|
{
|
||||||
|
nameBuffer.append( ' ' );
|
||||||
|
nameBuffer.append( ((IToken)i.next()).getImage() );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nameBuffer.toString();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue