1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-04-29 19:45:01 +02:00

Plain C: nested declarators for fields, bug 257540.

This commit is contained in:
Markus Schorn 2008-12-09 13:27:01 +00:00
parent 4ad132f821
commit d5d62baf17
3 changed files with 77 additions and 79 deletions

View file

@ -5581,4 +5581,17 @@ public class AST2Tests extends AST2BaseTest {
assertEquals(0, children[0].getChildren().length);
}
}
// struct s {
// int (mem);
// };
// void foo() {
// struct s v;
// v.mem = 1;
// }
public void testNestedDeclarator_Bug257540() throws Exception {
final String code= getAboveComment();
parseAndCheckBindings(code, ParserLanguage.C);
parseAndCheckBindings(code, ParserLanguage.CPP);
}
}

View file

@ -32,6 +32,7 @@ import org.eclipse.cdt.core.dom.ast.c.ICASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.c.ICASTElaboratedTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.c.ICCompositeTypeScope;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.CharArrayUtils;
import org.eclipse.cdt.internal.core.dom.Linkage;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
@ -156,67 +157,65 @@ public class CStructure extends PlatformObject implements ICompositeType, ICInte
return (IField[]) ArrayUtil.trim( IField.class, fields );
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.ICompositeType#findField(org.eclipse.cdt.core.dom.ast.IASTName)
*/
public IField findField(String name) throws DOMException {
if( definition == null ){
ICASTCompositeTypeSpecifier temp = checkForDefinition( (IASTElaboratedTypeSpecifier) declarations[0].getParent() );
if( temp == null )
return new CField.CFieldProblem( declarations[0], IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray() );
definition = temp.getName();
}
ICCompositeTypeScope scope = (ICCompositeTypeScope) getCompositeScope();
if( scope != null && ASTInternal.isFullyCached(scope) ){
IBinding binding = scope.getBinding( name.toCharArray() );
if( binding instanceof IField )
return (IField) binding;
} else {
ICASTCompositeTypeSpecifier compSpec = (ICASTCompositeTypeSpecifier) definition.getParent();
ICASTCompositeTypeSpecifier [] specStack = null;
int stackIdx = -1;
IASTDeclaration[] members = compSpec.getMembers();
IField found = null;
while( members != null ){
int size = members.length;
for( int i = 0; i < size; i++ ){
IASTNode node = members[i];
if( node instanceof IASTSimpleDeclaration ){
IASTDeclarator[] declarators = ((IASTSimpleDeclaration)node).getDeclarators();
for( int j = 0; j < declarators.length; j++ ){
IASTDeclarator declarator = declarators[j];
IASTName dtorName = declarator.getName();
if( scope != null )
ASTInternal.addName( scope, dtorName );
if( name.equals( dtorName.toString() ) ){
IBinding binding = dtorName.resolveBinding();
if( binding instanceof IField )
found = (IField) binding;
}
}
//anonymous structurs and unions
if( declarators.length == 0 && ((IASTSimpleDeclaration)node).getDeclSpecifier() instanceof IASTCompositeTypeSpecifier ){
IASTCompositeTypeSpecifier declSpec = (IASTCompositeTypeSpecifier) ((IASTSimpleDeclaration)node).getDeclSpecifier();
IASTName n = declSpec.getName();
if( n.toCharArray().length == 0 ){
specStack = (ICASTCompositeTypeSpecifier[])ArrayUtil.append( ICASTCompositeTypeSpecifier.class, specStack, declSpec );
}
}
}
}
if( specStack != null && ++stackIdx < specStack.length && specStack[stackIdx] != null ){
members = specStack[stackIdx].getMembers();
} else {
members = null;
}
}
if( scope != null )
ASTInternal.setFullyCached(scope, true);
if( found != null )
return found;
}
if (definition == null) {
ICASTCompositeTypeSpecifier temp = checkForDefinition((IASTElaboratedTypeSpecifier) declarations[0].getParent());
if (temp == null)
return new CField.CFieldProblem(declarations[0], IProblemBinding.SEMANTIC_DEFINITION_NOT_FOUND, getNameCharArray());
definition = temp.getName();
}
final char[] nchars= name.toCharArray();
ICCompositeTypeScope scope = (ICCompositeTypeScope) getCompositeScope();
if (scope != null && ASTInternal.isFullyCached(scope)) {
IBinding binding = scope.getBinding(nchars);
if (binding instanceof IField)
return (IField) binding;
} else {
ICASTCompositeTypeSpecifier compSpec = (ICASTCompositeTypeSpecifier) definition.getParent();
ICASTCompositeTypeSpecifier[] specStack = null;
int stackIdx = -1;
IASTDeclaration[] members = compSpec.getMembers();
IField found = null;
while (members != null) {
int size = members.length;
for (int i = 0; i < size; i++) {
IASTNode node = members[i];
if (node instanceof IASTSimpleDeclaration) {
IASTDeclarator[] declarators = ((IASTSimpleDeclaration) node).getDeclarators();
for (int j = 0; j < declarators.length; j++) {
IASTDeclarator declarator = declarators[j];
IASTName dtorName = CVisitor.findInnermostDeclarator(declarator).getName();
if (scope != null)
ASTInternal.addName(scope, dtorName);
if (CharArrayUtils.equals(nchars, dtorName.toCharArray())) {
IBinding binding = dtorName.resolveBinding();
if (binding instanceof IField)
found = (IField) binding;
}
}
// anonymous structures and unions
if (declarators.length == 0 && ((IASTSimpleDeclaration) node).getDeclSpecifier() instanceof IASTCompositeTypeSpecifier) {
IASTCompositeTypeSpecifier declSpec = (IASTCompositeTypeSpecifier) ((IASTSimpleDeclaration) node).getDeclSpecifier();
IASTName n = declSpec.getName();
if (n.toCharArray().length == 0) {
specStack = (ICASTCompositeTypeSpecifier[]) ArrayUtil.append(ICASTCompositeTypeSpecifier.class, specStack, declSpec);
}
}
}
}
if (specStack != null && ++stackIdx < specStack.length && specStack[stackIdx] != null) {
members = specStack[stackIdx].getMembers();
} else {
members = null;
}
}
if (scope != null)
ASTInternal.setFullyCached(scope, true);
if (found != null)
return found;
}
return null;
}

View file

@ -886,32 +886,18 @@ public class CVisitor {
private static IBinding createBinding(IASTDeclarator declarator) {
IASTNode parent = declarator.getParent();
while (parent instanceof IASTDeclarator) {
parent = parent.getParent();
}
while (declarator.getNestedDeclarator() != null)
declarator = declarator.getNestedDeclarator();
declarator= CVisitor.findInnermostDeclarator(declarator);
IASTDeclarator typeRelevant= CVisitor.findTypeRelevantDeclarator(declarator);
IASTFunctionDeclarator funcDeclarator= null;
IASTNode node= declarator;
do {
if (node instanceof IASTFunctionDeclarator) {
funcDeclarator= (IASTFunctionDeclarator) node;
break;
}
if (((IASTDeclarator) node).getPointerOperators().length > 0 ||
node.getPropertyInParent() != IASTDeclarator.NESTED_DECLARATOR) {
break;
}
node= node.getParent();
if (typeRelevant instanceof IASTFunctionDeclarator) {
funcDeclarator= (IASTFunctionDeclarator) typeRelevant;
}
while (node instanceof IASTDeclarator)
;
IScope scope = getContainingScope(parent);
IScope scope= getContainingScope(parent);
ASTNodeProperty prop = parent.getPropertyInParent();
if (prop == IASTDeclarationStatement.DECLARATION) {
//implicit scope, see 6.8.4-3