1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-08-20 22:55:51 +02:00

Patch for Andrew Niefer

This patch improves support in the parser symbol table for forward declarations
This commit is contained in:
John Camelon 2003-08-01 17:43:10 +00:00
parent 8513838955
commit 87e177ade2
6 changed files with 215 additions and 24 deletions

View file

@ -1,3 +1,7 @@
2003-07-31 Andrew Niefer
Added ParserSymbolTableTest.testForwardClassDeclaration
Added ParserSymbolTableTest.testForwardDeclarationUsedAsFunctionParam
2003-07-31 Victor Mozgin 2003-07-31 Victor Mozgin
Moved testBug39540() from ASTFailedTests.java to QuickParseASTTests.java. Moved testBug39540() from ASTFailedTests.java to QuickParseASTTests.java.

View file

@ -1573,7 +1573,7 @@ public class ParserSymbolTableTest extends TestCase {
* @throws Exception * @throws Exception
* *
* class A {}; * class A {};
* typedef A * B; * typedef B A *;
* *
* void f( A * ); * void f( A * );
* void f( A ); * void f( A );
@ -1600,6 +1600,7 @@ public class ParserSymbolTableTest extends TestCase {
ISymbol B = table.newSymbol( "B" ); ISymbol B = table.newSymbol( "B" );
B.setType( TypeInfo.t_type ); B.setType( TypeInfo.t_type );
B.setTypeSymbol( A ); B.setTypeSymbol( A );
B.getTypeInfo().setBit( true, TypeInfo.isTypedef );
B.addPtrOperator( new PtrOp( PtrOp.t_pointer, false, false ) ); B.addPtrOperator( new PtrOp( PtrOp.t_pointer, false, false ) );
compUnit.addSymbol( B ); compUnit.addSymbol( B );
@ -2331,5 +2332,145 @@ public class ParserSymbolTableTest extends TestCase {
assertEquals( e.reason, ParserSymbolTableException.r_Ambiguous ); assertEquals( e.reason, ParserSymbolTableException.r_Ambiguous );
} }
} }
/**
* class A;
*
* A * a;
*
* class A {};
*
* @throws Exception
*/
public void testForwardClassDeclaration() throws Exception{
newTable();
ISymbol forwardSymbol = table.newDerivableContainerSymbol( "A", TypeInfo.t_class );
forwardSymbol.setIsForwardDeclaration( true );
table.getCompilationUnit().addSymbol( forwardSymbol );
/*...*/
ISymbol lookup = table.getCompilationUnit().Lookup( "A" );
ISymbol otherLookup = table.getCompilationUnit().ElaboratedLookup( TypeInfo.t_class, "A" );
assertEquals( lookup, otherLookup );
assertEquals( lookup, forwardSymbol );
ISymbol a = table.newSymbol( "a", TypeInfo.t_type );
a.setTypeSymbol( forwardSymbol );
a.addPtrOperator( new PtrOp( PtrOp.t_pointer ) );
table.getCompilationUnit().addSymbol( a );
/*...*/
lookup = table.getCompilationUnit().Lookup( "A" );
IDerivableContainerSymbol classA = table.newDerivableContainerSymbol( "A", TypeInfo.t_class );
assertTrue( lookup.isForwardDeclaration() );
lookup.setTypeSymbol( classA );
table.getCompilationUnit().addSymbol( classA );
lookup = table.getCompilationUnit().Lookup( "a" );
assertEquals( lookup, a );
assertEquals( a.getTypeSymbol(), classA );
lookup = table.getCompilationUnit().Lookup( "A" );
assertEquals( lookup, classA );
lookup = table.getCompilationUnit().ElaboratedLookup( TypeInfo.t_class, "A" );
assertEquals( lookup, classA );
}
/**
* class A;
*
* class B {
* static void f( A * );
* static void f( int );
* };
*
* A* a1;
*
* class A {};
*
* void B::f( A * ) {}
* void B::f( int ) {}
*
* A* a2;
*
* B::f( a1 );
* B::f( a2 );
*
* @throws Exception
*/
public void testForwardDeclarationUsedAsFunctionParam() throws Exception{
newTable();
ISymbol forwardSymbol = table.newDerivableContainerSymbol( "A", TypeInfo.t_class );
forwardSymbol.setIsForwardDeclaration( true );
table.getCompilationUnit().addSymbol( forwardSymbol );
/*...*/
IDerivableContainerSymbol classB = table.newDerivableContainerSymbol( "B", TypeInfo.t_class );
IParameterizedSymbol fn1 = table.newParameterizedSymbol( "f", TypeInfo.t_function );
ISymbol lookup = table.getCompilationUnit().Lookup( "A" );
assertEquals( lookup, forwardSymbol );
fn1.addParameter( lookup, new PtrOp( PtrOp.t_pointer ), false );
fn1.getTypeInfo().setBit( true, TypeInfo.isStatic );
classB.addSymbol( fn1 );
IParameterizedSymbol fn2 = table.newParameterizedSymbol( "f", TypeInfo.t_function );
fn2.addParameter( TypeInfo.t_int, 0, null, false );
fn2.getTypeInfo().setBit( true, TypeInfo.isStatic );
classB.addSymbol( fn2 );
table.getCompilationUnit().addSymbol( classB );
/*...*/
ISymbol a1 = table.newSymbol( "a1", TypeInfo.t_type );
lookup = table.getCompilationUnit().Lookup( "A" );
assertEquals( lookup, forwardSymbol );
a1.setTypeSymbol( lookup );
a1.addPtrOperator( new PtrOp( PtrOp.t_pointer ) );
table.getCompilationUnit().addSymbol( a1 );
/*...*/
lookup = table.getCompilationUnit().Lookup( "A" );
IDerivableContainerSymbol classA = table.newDerivableContainerSymbol( "A", TypeInfo.t_class );
assertTrue( lookup.isForwardDeclaration() );
lookup.setTypeSymbol( classA );
table.getCompilationUnit().addSymbol( classA );
/*..*/
ISymbol a2 = table.newSymbol( "a2", TypeInfo.t_type );
lookup = table.getCompilationUnit().Lookup( "A" );
assertEquals( lookup, classA );
a2.setTypeSymbol( lookup );
a2.addPtrOperator( new PtrOp( PtrOp.t_pointer ) );
table.getCompilationUnit().addSymbol( a2 );
/*..*/
LinkedList paramList = new LinkedList();
TypeInfo p1 = new TypeInfo( TypeInfo.t_type, 0, a1 );
paramList.add( p1 );
ISymbol look = classB.MemberFunctionLookup( "f", paramList );
assertEquals( look, fn1 );
paramList.clear();
p1 = new TypeInfo( TypeInfo.t_type, 0, a2 );
paramList.add( p1 );
look = classB.MemberFunctionLookup( "f", paramList );
assertEquals( look, fn1 );
}
} }

View file

@ -1,3 +1,6 @@
2003-07-31 Andrew Niefer
Added better support to the parser symbol table for forward declarations
2003-07-31 Victor Mozgin 2003-07-31 Victor Mozgin
Fixed PR 39540 : Parser fails on const qualifier after class specifier. Fixed PR 39540 : Parser fails on const qualifier after class specifier.

View file

@ -41,6 +41,9 @@ public interface ISymbol extends Cloneable {
public ISymbol getTypeSymbol(); public ISymbol getTypeSymbol();
public void setTypeSymbol( ISymbol type ); public void setTypeSymbol( ISymbol type );
public boolean isForwardDeclaration();
public void setIsForwardDeclaration( boolean forward );
public int compareCVQualifiersTo( ISymbol symbol ); public int compareCVQualifiersTo( ISymbol symbol );
public LinkedList getPtrOperators(); public LinkedList getPtrOperators();
public void addPtrOperator( TypeInfo.PtrOp ptrOp ); public void addPtrOperator( TypeInfo.PtrOp ptrOp );

View file

@ -440,6 +440,13 @@ public class ParserSymbolTable {
TypeInfo.eType origType = origSymbol.getType(); TypeInfo.eType origType = origSymbol.getType();
TypeInfo.eType newType = newSymbol.getType(); TypeInfo.eType newType = newSymbol.getType();
//handle forward decls
if( origSymbol.getTypeInfo().isForwardDeclaration() &&
origSymbol.getTypeSymbol() == newSymbol )
{
return true;
}
if( (origType.compareTo(TypeInfo.t_class) >= 0 && origType.compareTo(TypeInfo.t_enumeration) <= 0) && //class name or enumeration ... if( (origType.compareTo(TypeInfo.t_class) >= 0 && origType.compareTo(TypeInfo.t_enumeration) <= 0) && //class name or enumeration ...
( newType == TypeInfo.t_type || (newType.compareTo( TypeInfo.t_function ) >= 0 /*&& newType <= TypeInfo.typeMask*/) ) ){ ( newType == TypeInfo.t_type || (newType.compareTo( TypeInfo.t_function ) >= 0 /*&& newType <= TypeInfo.typeMask*/) ) ){
@ -570,10 +577,17 @@ public class ParserSymbolTable {
} else { } else {
//if this is a class-name, other stuff hides it //if this is a class-name, other stuff hides it
if( decl.isType( TypeInfo.t_class, TypeInfo.t_enumeration ) ){ if( decl.isType( TypeInfo.t_class, TypeInfo.t_enumeration ) ){
if( cls == null ) { if( cls == null ){
cls = (IContainerSymbol) decl; cls = (IContainerSymbol) decl;
} else { } else {
throw new ParserSymbolTableException( ParserSymbolTableException.r_Ambiguous ); if( cls.getTypeInfo().isForwardDeclaration() && cls.getTypeSymbol() == decl ){
//cls is a forward declaration of decl, we want decl.
cls = (IContainerSymbol) decl;
} else if( decl.getTypeInfo().isForwardDeclaration() && decl.getTypeSymbol() == cls ){
//decl is a forward declaration of cls, we already have what we want (cls)
} else {
throw new ParserSymbolTableException( ParserSymbolTableException.r_Ambiguous );
}
} }
} else { } else {
//an object, can only have one of these //an object, can only have one of these
@ -1049,6 +1063,15 @@ public class ParserSymbolTable {
source = getFlatTypeInfo( source ); source = getFlatTypeInfo( source );
} }
if( target.isType( TypeInfo.t_type ) ){
ISymbol symbol = target.getTypeSymbol();
if( symbol != null && symbol.isForwardDeclaration() && symbol.getTypeSymbol() != null ){
target = new TypeInfo( target );
target.setType( TypeInfo.t_type );
target.setTypeSymbol( symbol.getTypeSymbol() );
}
}
Cost cost = new Cost( source, target ); Cost cost = new Cost( source, target );
TypeInfo.PtrOp op = null; TypeInfo.PtrOp op = null;
@ -1401,7 +1424,7 @@ public class ParserSymbolTable {
info = topInfo.getTypeSymbol().getTypeInfo(); info = topInfo.getTypeSymbol().getTypeInfo();
while( info.getType() == TypeInfo.t_type ){ while( info.getType() == TypeInfo.t_type || ( info.isForwardDeclaration() && info.getTypeSymbol() != null ) ){
typeSymbol = info.getTypeSymbol(); typeSymbol = info.getTypeSymbol();
//returnInfo.addCVQualifier( info.getCVQualifier() ); //returnInfo.addCVQualifier( info.getCVQualifier() );
@ -2045,7 +2068,7 @@ public class ParserSymbolTable {
{ {
super(); super();
_name = name; _name = name;
_typeInfo = new TypeInfo( typeInfo, 0, this ); _typeInfo = new TypeInfo( typeInfo, 0, null );
} }
public ParserSymbolTable getSymbolTable(){ public ParserSymbolTable getSymbolTable(){
@ -2077,27 +2100,33 @@ public class ParserSymbolTable {
} }
public void setType(TypeInfo.eType t){ public void setType(TypeInfo.eType t){
_typeInfo.setType( t ); getTypeInfo().setType( t );
} }
public TypeInfo.eType getType(){ public TypeInfo.eType getType(){
return _typeInfo.getType(); return getTypeInfo().getType();
} }
public boolean isType( TypeInfo.eType type ){ public boolean isType( TypeInfo.eType type ){
return _typeInfo.isType( type, TypeInfo.t_undef ); return getTypeInfo().isType( type, TypeInfo.t_undef );
} }
public boolean isType( TypeInfo.eType type, TypeInfo.eType upperType ){ public boolean isType( TypeInfo.eType type, TypeInfo.eType upperType ){
return _typeInfo.isType( type, upperType ); return getTypeInfo().isType( type, upperType );
} }
public ISymbol getTypeSymbol(){ public ISymbol getTypeSymbol(){
return _typeInfo.getTypeSymbol(); ISymbol symbol = getTypeInfo().getTypeSymbol();
if( symbol != null && symbol.getTypeInfo().isForwardDeclaration() && symbol.getTypeSymbol() != null ){
return symbol.getTypeSymbol();
}
return symbol;
} }
public void setTypeSymbol( ISymbol type ){ public void setTypeSymbol( ISymbol type ){
_typeInfo.setTypeSymbol( type ); getTypeInfo().setTypeSymbol( type );
} }
public TypeInfo getTypeInfo(){ public TypeInfo getTypeInfo(){
@ -2108,6 +2137,14 @@ public class ParserSymbolTable {
_typeInfo = info; _typeInfo = info;
} }
public boolean isForwardDeclaration(){
return getTypeInfo().isForwardDeclaration();
}
public void setIsForwardDeclaration( boolean forward ){
getTypeInfo().setIsForwardDeclaration( forward );
}
/** /**
* returns 0 if same, non zero otherwise * returns 0 if same, non zero otherwise
*/ */
@ -2141,10 +2178,10 @@ public class ParserSymbolTable {
} }
public LinkedList getPtrOperators(){ public LinkedList getPtrOperators(){
return _typeInfo.getPtrOperators(); return getTypeInfo().getPtrOperators();
} }
public void addPtrOperator( TypeInfo.PtrOp ptrOp ){ public void addPtrOperator( TypeInfo.PtrOp ptrOp ){
_typeInfo.addPtrOperator( ptrOp ); getTypeInfo().addPtrOperator( ptrOp );
} }
public int getDepth(){ public int getDepth(){
@ -2391,12 +2428,6 @@ public class ParserSymbolTable {
_needsDefinition = need; _needsDefinition = need;
} }
//public void addPtrOperator( String ptrStr, boolean isConst, boolean isVolatile ){
// _typeInfo.addPtrOperator( ptrStr, isConst, isVolatile );
//}
public ISymbol getReturnType(){ public ISymbol getReturnType(){
return _returnType; return _returnType;
} }
@ -2555,11 +2586,11 @@ public class ParserSymbolTable {
if( origObj != null ) if( origObj != null )
{ {
Declaration origDecl = null; ISymbol origDecl = null;
LinkedList origList = null; LinkedList origList = null;
if( origObj.getClass() == Declaration.class ){ if( origObj instanceof ISymbol ){
origDecl = (Declaration)origObj; origDecl = (ISymbol)origObj;
} else if( origObj.getClass() == LinkedList.class ){ } else if( origObj.getClass() == LinkedList.class ){
origList = (LinkedList)origObj; origList = (LinkedList)origObj;
} else { } else {

View file

@ -84,6 +84,7 @@ public class TypeInfo {
public static final int isUnsigned = 0x20000; public static final int isUnsigned = 0x20000;
public static final int isShort = 0x40000; public static final int isShort = 0x40000;
public static final int isLong = 0x80000; public static final int isLong = 0x80000;
public static final int isForward = 0x100000;
// Types (maximum type is typeMask // Types (maximum type is typeMask
// Note that these should be considered ordered and if you change // Note that these should be considered ordered and if you change
@ -378,6 +379,14 @@ public class TypeInfo {
return _defaultValue; return _defaultValue;
} }
public boolean isForwardDeclaration(){
return checkBit( isForward );
}
public void setIsForwardDeclaration( boolean forward ){
setBit( forward, isForward );
}
/** /**
* canHold * canHold
* @param type * @param type