1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-08-09 01:05:38 +02:00

AST for inactive code, bug 264666.

This commit is contained in:
Markus Schorn 2009-02-24 16:01:32 +00:00
parent a401523e2f
commit 9f44be00ab
82 changed files with 1810 additions and 1270 deletions

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -129,6 +129,7 @@ public class AST2BaseTest extends BaseTestCase {
boolean expectNoProblems, boolean skipTrivialInitializers) throws ParserException {
IScanner scanner = createScanner(new CodeReader(code.toCharArray()), lang, ParserMode.COMPLETE_PARSE,
new ScannerInfo());
configureScanner(scanner);
AbstractGNUSourceCodeParser parser = null;
if (lang == ParserLanguage.CPP) {
ICPPParserExtensionConfiguration config = null;
@ -171,6 +172,9 @@ public class AST2BaseTest extends BaseTestCase {
return tu;
}
protected void configureScanner(IScanner scanner) {
}
public static IScanner createScanner(CodeReader codeReader, ParserLanguage lang, ParserMode mode,
IScannerInfo scannerInfo) {
IScannerExtensionConfiguration configuration = null;
@ -492,6 +496,16 @@ public class AST2BaseTest extends BaseTestCase {
return (T) binding;
}
public void assertNoName(String section, int len) {
final int offset = contents.indexOf(section);
assertTrue(offset >= 0);
final String selection = section.substring(0, len);
IASTName name= tu.getNodeSelector(null).findName(offset, len);
if (name != null) {
fail("Found unexpected \""+selection+"\": " + name.resolveBinding());
}
}
private String renderProblemID(int i) {
try {
for (Field field : IProblemBinding.class.getDeclaredFields()) {
@ -523,6 +537,7 @@ public class AST2BaseTest extends BaseTestCase {
private IBinding binding(String section, int len) {
final int offset = contents.indexOf(section);
assertTrue(offset >= 0);
final String selection = section.substring(0, len);
IASTName name= tu.getNodeSelector(null).findName(offset, len);
assertNotNull("did not find \""+selection+"\"", name);

View file

@ -0,0 +1,403 @@
/*******************************************************************************
* 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.parser.tests.ast2;
import java.util.BitSet;
import junit.framework.TestSuite;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.dom.ast.IField;
import org.eclipse.cdt.core.dom.ast.IFunction;
import org.eclipse.cdt.core.dom.ast.IVariable;
import org.eclipse.cdt.core.parser.IScanner;
import org.eclipse.cdt.core.parser.ParserLanguage;
/**
* Testcases for inactive code in ast.
*/
public class ASTInactiveCodeTests extends AST2BaseTest {
public static TestSuite suite() {
return suite(ASTInactiveCodeTests.class);
}
public ASTInactiveCodeTests() {
super();
}
public ASTInactiveCodeTests(String name) {
super(name);
}
@Override
protected void configureScanner(IScanner scanner) {
super.configureScanner(scanner);
scanner.setProcessInactiveCode(true);
}
// #if %
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
public void testIfBranches() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.C, i);
}
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i);
}
}
private void testBranches(String codeTmpl, ParserLanguage lang, int bits) throws Exception {
testBranches(codeTmpl, lang, bits, 0);
}
private void testBranches(String codeTmpl, ParserLanguage lang, int bits, int level) throws Exception {
BitSet bs= convert(bits);
char[] chars= codeTmpl.toCharArray();
int pos= codeTmpl.indexOf('%', 0);
int i= 0;
while (pos >= 0) {
chars[pos]= bs.get(i++) ? '1' : '0';
pos= codeTmpl.indexOf('%', pos+1);
}
IASTDeclarationListOwner tu= parse(new String(chars), lang);
while (level-- > 0) {
final IASTDeclaration decl = tu.getDeclarations(true)[0];
if (decl instanceof IASTSimpleDeclaration) {
tu= (IASTDeclarationListOwner) ((IASTSimpleDeclaration) decl).getDeclSpecifier();
} else {
tu= (IASTDeclarationListOwner) decl;
}
}
IASTDeclaration[] decl= tu.getDeclarations(true);
assertEquals(8, decl.length);
assertEquals(bs.get(0), decl[0].isActive());
assertEquals(!bs.get(0) && bs.get(1), decl[1].isActive());
assertEquals(!bs.get(0) && bs.get(1) && bs.get(2), decl[2].isActive());
assertEquals(!bs.get(0) && bs.get(1) && !bs.get(2) && bs.get(3), decl[3].isActive());
assertEquals(!bs.get(0) && bs.get(1) && !bs.get(2) && !bs.get(3), decl[4].isActive());
assertEquals(!bs.get(0) && bs.get(1), decl[5].isActive());
assertEquals(!bs.get(0) && !bs.get(1), decl[6].isActive());
assertEquals(true, decl[7].isActive());
}
private BitSet convert(int bits) {
BitSet result= new BitSet(32);
for (int i = 0; i < 32; i++) {
if ((bits & (1 << i)) != 0) {
result.set(i);
}
}
return result;
}
// #define A1
// #ifdef A%
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
public void testIfdefBranches() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.C, i);
}
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i);
}
}
// #define A0
// #ifndef A%
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
public void testIfndefBranches() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.C, i);
}
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i);
}
}
// struct S {
// #if %
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
// };
public void testStructs() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.C, i, 1);
}
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i, 1);
}
}
// extern "C" {
// #if %
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
// };
public void testExternC() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i, 1);
}
}
// namespace ns {
// #if %
// int a0;
// #elif %
// int a1;
// #if %
// int a2;
// #elif %
// int a3;
// #else
// int a4;
// #endif
// int a5;
// #else
// int a6;
// #endif
// int a7;
// }
public void testNamespace() throws Exception {
String codeTmpl= getAboveComment();
for (int i= 0; i < (1<<4); i++) {
testBranches(codeTmpl, ParserLanguage.CPP, i, 1);
}
}
// typedef int TInt;
// const int value= 12;
// #if 0
// int f(TInt);
// int g(value);
// #endif
public void testAmbiguity() throws Exception {
String code= getAboveComment();
IASTTranslationUnit tu= parseAndCheckBindings(code, ParserLanguage.CPP);
IASTDeclaration[] decls = tu.getDeclarations(true);
IASTSimpleDeclaration decl= (IASTSimpleDeclaration) decls[2];
assertTrue(decl.getDeclarators()[0] instanceof IASTFunctionDeclarator);
decl= (IASTSimpleDeclaration) decls[3];
assertFalse(decl.getDeclarators()[0] instanceof IASTFunctionDeclarator);
}
// int a; // 1
// #if 0
// int a; // 2
// #if 0
// int a; // 3
// #endif
// int b; // 1
// #endif
// int b; // 2
public void testDuplicateDefinition() throws Exception {
String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, false);
bh.assertNonProblem("a; // 1", 1);
bh.assertNonProblem("a; // 2", 1);
bh.assertNonProblem("a; // 3", 1);
bh.assertNonProblem("b; // 1", 1);
bh.assertNonProblem("b; // 2", 1);
bh= new BindingAssertionHelper(code, true);
bh.assertNonProblem("a; // 1", 1);
bh.assertNonProblem("a; // 2", 1);
bh.assertNonProblem("a; // 3", 1);
bh.assertNonProblem("b; // 1", 1);
bh.assertNonProblem("b; // 2", 1);
parseAndCheckBindings(code, ParserLanguage.C);
parseAndCheckBindings(code, ParserLanguage.CPP);
}
// struct S {
// #if 0
// int a;
// };
// #else
// int b;
// };
// #endif
public void testInactiveClosingBrace() throws Exception {
String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, false);
IField a= bh.assertNonProblem("a;", 1);
IField b= bh.assertNonProblem("b;", 1);
assertSame(a.getOwner(), b.getOwner());
bh= new BindingAssertionHelper(code, true);
a= bh.assertNonProblem("a;", 1);
b= bh.assertNonProblem("b;", 1);
assertSame(a.getOwner(), b.getOwner());
}
// struct S
// #if 1
// {
// int a;
// #else
// int b;
// #endif
// int c;
// #if 0
// int d;
// #endif
// };
public void testOpenBraceInActiveBranch() throws Exception {
String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, false);
IField a= bh.assertNonProblem("a;", 1);
bh.assertNoName("b;", 1);
IField c= bh.assertNonProblem("c;", 1);
IField d= bh.assertNonProblem("d;", 1);
assertSame(a.getOwner(), c.getOwner());
assertSame(a.getOwner(), d.getOwner());
bh= new BindingAssertionHelper(code, true);
a= bh.assertNonProblem("a;", 1);
bh.assertNoName("b;", 1);
c= bh.assertNonProblem("c;", 1);
d= bh.assertNonProblem("d;", 1);
assertSame(a.getOwner(), c.getOwner());
assertSame(a.getOwner(), d.getOwner());
}
// #if 0
// struct S {
// #if 1
// int a;
// #else
// int b;
// #endif
// #elif 0
// int c;
// #endif
// int d;
public void testOpenBraceInInactiveBranch() throws Exception {
String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, false);
IField a= bh.assertNonProblem("a;", 1);
IField b= bh.assertNonProblem("b;", 1);
IVariable c= bh.assertNonProblem("c;", 1); // part of a different non-nested branch
IVariable d= bh.assertNonProblem("d;", 1);
assertSame(a.getOwner(), b.getOwner());
assertNull(c.getOwner());
assertNull(d.getOwner());
bh= new BindingAssertionHelper(code, true);
a= bh.assertNonProblem("a;", 1);
b= bh.assertNonProblem("b;", 1);
c= bh.assertNonProblem("c;", 1); // part of a different non-nested branch
d= bh.assertNonProblem("d;", 1);
assertSame(a.getOwner(), b.getOwner());
assertNull(c.getOwner());
assertNull(d.getOwner());
}
// #if 0
// void f() {
// #if 1
// int a;
// #elif 0
// int b;
// #endif
// }
// #endif
public void testUnexpectedBranchesInInactiveCode() throws Exception {
String code= getAboveComment();
BindingAssertionHelper bh= new BindingAssertionHelper(code, false);
IFunction f= bh.assertNonProblem("f()", 1);
bh.assertNoName("a;", 1);
bh.assertNoName("b;", 1);
bh= new BindingAssertionHelper(code, true);
f= bh.assertNonProblem("f()", 1);
bh.assertNoName("a;", 1);
bh.assertNoName("b;", 1);
}
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -52,6 +52,7 @@ public class DOMParserTestSuite extends TestCase {
suite.addTestSuite(CharArrayMapTest.class);
suite.addTest(FaultToleranceTests.suite());
suite.addTest(LanguageExtensionsTest.suite());
suite.addTest(ASTInactiveCodeTests.suite());
return suite;
}
}

View file

@ -14,7 +14,9 @@ package org.eclipse.cdt.core.model;
import org.eclipse.cdt.core.dom.ICodeReaderFactory;
import org.eclipse.cdt.core.dom.ILinkage;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTCompletionNode;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.index.IIndex;
@ -69,9 +71,13 @@ public interface ILanguage extends IAdaptable {
/**
* Option for {@link #getASTTranslationUnit(CodeReader, IScannerInfo, ICodeReaderFactory, IIndex, int, IParserLogService)}
* Instructs the parser to create ast nodes for inactive code branches, if possible. There is no guarantee that the ast
* can actually be created for the inactive parts.
* mstodo document how the ast can be accessed.
* Instructs the parser to create ast nodes for inactive code branches, if possible. The parser
* makes its best effort to create ast for the inactive code branches but may decide to skip parts
* of the inactive code (e.g. function bodies, entire code branches, etc.).
* <p>
* The inactive nodes can be accessed via {@link IASTDeclarationListOwner#getDeclarations(boolean)} or
* by using a visitor with {@link ASTVisitor#includeInactiveNodes} set to <code>true</code>.
*
* @since 5.1
*/
public final static int OPTION_PARSE_INACTIVE_CODE= 0x20;

View file

@ -13,7 +13,9 @@ package org.eclipse.cdt.core.model;
import java.util.Map;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTCompletionNode;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.index.IIndex;
import org.eclipse.cdt.core.parser.CodeReader;
@ -97,8 +99,13 @@ public interface ITranslationUnit extends ICElement, IParent, IOpenable, ISource
/**
* Style constant for {@link #getAST(IIndex, int)}.
* Instructs the parser to make an attempt to create ast nodes for inactive code branches.
* mstodo document how to access those.
* Instructs the parser to make an attempt to create ast nodes for inactive code branches. The parser
* makes its best effort to create ast for the inactive code branches but may decide to skip parts
* of the inactive code (e.g. function bodies, entire code branches, etc.).
* <p>
* The inactive nodes can be accessed via {@link IASTDeclarationListOwner#getDeclarations(boolean)} or
* by using a visitor with {@link ASTVisitor#includeInactiveNodes} set to <code>true</code>.
*
* @since 5.1
*/
public final static int AST_PARSE_INACTIVE_CODE= 0x80;

View file

@ -210,7 +210,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
}
}
// declarations
final IASTDeclaration[] declarations= ast.getDeclarations();
final IASTDeclaration[] declarations= ast.getDeclarations(true);
for (IASTDeclaration declaration : declarations) {
if (isLocalToFile(declaration)) {
createDeclaration(fTranslationUnit, declaration);
@ -405,7 +405,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
* @throws DOMException
*/
private void createLinkageSpecification(Parent parent, ICPPASTLinkageSpecification linkageDeclaration) throws CModelException, DOMException {
IASTDeclaration[] declarations= linkageDeclaration.getDeclarations();
IASTDeclaration[] declarations= linkageDeclaration.getDeclarations(true);
for (IASTDeclaration declaration : declarations) {
if (linkageDeclaration.getFileLocation() != null || isLocalToFile(declaration)) {
createDeclaration(parent, declaration);
@ -489,6 +489,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
final String nsName= ASTStringUtil.getQualifiedName(name);
final Namespace element= new Namespace(parent, nsName);
setIndex(element);
element.setActive(declaration.isActive());
// add to parent
parent.addChild(element);
@ -505,7 +506,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
element.setTypeName(type);
IASTDeclaration[] nsDeclarations= declaration.getDeclarations();
IASTDeclaration[] nsDeclarations= declaration.getDeclarations(true);
for (IASTDeclaration nsDeclaration : nsDeclarations) {
if (declaration.getFileLocation() != null || isLocalToFile(nsDeclaration)) {
createDeclaration(element, nsDeclaration);
@ -551,6 +552,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
element= new StructureDeclaration(parent, className, kind);
}
setIndex(element);
element.setActive(elaboratedTypeSpecifier.isActive());
element.setTypeName(type);
// add to parent
@ -576,6 +578,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
final String enumName= ASTStringUtil.getSimpleName(astEnumName);
final Enumeration element= new Enumeration (parent, enumName);
setIndex(element);
element.setActive(enumSpecifier.isActive());
// add to parent
parent.addChild(element);
@ -599,6 +602,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
final IASTName astEnumName= enumDef.getName();
final Enumerator element= new Enumerator (enumarator, ASTStringUtil.getSimpleName(astEnumName));
setIndex(element);
element.setActive(enumDef.isActive());
IASTExpression initialValue= enumDef.getValue();
if(initialValue != null){
@ -652,6 +656,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
element= classTemplate;
}
setIndex(element);
element.setActive(compositeTypeSpecifier.isActive());
if (compositeTypeSpecifier instanceof ICPPASTCompositeTypeSpecifier) {
// store super classes names
@ -696,7 +701,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
// add members
pushDefaultVisibility(defaultVisibility);
try {
final IASTDeclaration[] memberDeclarations= compositeTypeSpecifier.getMembers();
final IASTDeclaration[] memberDeclarations= compositeTypeSpecifier.getDeclarations(true);
for (IASTDeclaration member : memberDeclarations) {
if (compositeTypeSpecifier.getFileLocation() != null || isLocalToFile(member)) {
createDeclaration(element, member);
@ -722,6 +727,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
final TypeDef element= new TypeDef(parent, name);
setIndex(element);
element.setActive(declarator.isActive());
String typeName= ASTStringUtil.getSignatureString(declSpecifier, declarator);
element.setTypeName(typeName);
@ -792,6 +798,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
element.setTypeName(ASTStringUtil.getSignatureString(specifier, declarator));
info= element.getSourceManipulationInfo();
}
element.setActive(declarator.isActive());
element.setConst(specifier.isConst());
element.setVolatile(specifier.isVolatile());
// TODO [cmodel] correctly resolve isStatic
@ -958,6 +965,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
info= element.getFunctionInfo();
}
element.setActive(functionDeclaration.isActive());
// TODO [cmodel] correctly resolve isStatic
info.setStatic(declSpecifier.getStorageClass() == IASTDeclSpecifier.sc_static);
@ -1048,6 +1056,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
assert false;
return null;
}
element.setActive(declarator.isActive());
// TODO [cmodel] correctly resolve isStatic
info.setStatic(declSpecifier.getStorageClass() == IASTDeclSpecifier.sc_static);
@ -1068,6 +1077,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
IASTName name= usingDirDeclaration.getQualifiedName();
Using element= new Using(parent, ASTStringUtil.getQualifiedName(name), true);
setIndex(element);
element.setActive(usingDirDeclaration.isActive());
// add to parent
parent.addChild(element);
@ -1083,7 +1093,7 @@ public class CModelBuilder2 implements IContributedModelBuilder {
IASTName name= usingDeclaration.getName();
Using element= new Using(parent, ASTStringUtil.getSimpleName(name), false);
setIndex(element);
element.setActive(usingDeclaration.isActive());
// add to parent
parent.addChild(element);

View file

@ -119,6 +119,13 @@ public abstract class ASTVisitor {
*/
public boolean shouldVisitTemplateParameters = false;
/**
* Per default inactive nodes are not visited. You can change that by setting
* this flag to <code>true</code>.
* @since 5.1
*/
public boolean includeInactiveNodes= false;
/**
* For internal use, only.
* @noreference This field is not intended to be referenced by clients.
@ -134,7 +141,8 @@ public abstract class ASTVisitor {
/**
* Creates a visitor.
* @param visitNodes whether visitor is setup to visit all nodes per default.
* @param visitNodes whether visitor is setup to visit all nodes per default, except
* ambiguous nodes ({@link #shouldVisitAmbiguousNodes}) and inactive nodes ({@link #includeInactiveNodes}).
* @since 5.1
*/
public ASTVisitor(boolean visitNodes) {

View file

@ -17,7 +17,7 @@ package org.eclipse.cdt.core.dom.ast;
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface IASTCompositeTypeSpecifier extends IASTDeclSpecifier , IASTNameOwner {
public interface IASTCompositeTypeSpecifier extends IASTDeclSpecifier , IASTNameOwner, IASTDeclarationListOwner {
/**
* <code>TYPE_NAME</code> represents the relationship between an

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;
import org.eclipse.cdt.core.model.ITranslationUnit;
/**
* Common interface for parents of declaration lists.
* @since 5.1
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface IASTDeclarationListOwner extends IASTNode {
/**
* Adds a declaration to the owner. May only be called as long as the ast is not frozen.
*/
void addDeclaration(IASTDeclaration declaration);
/**
* Returns the array of declarations.
* @param includeInactive whether to include declarations from inactive code branches.
* @see ITranslationUnit#AST_PARSE_INACTIVE_CODE
* @since 5.1
*/
IASTDeclaration[] getDeclarations(boolean includeInactive);
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -208,6 +208,11 @@ public interface IASTNode {
*/
public boolean isFrozen();
/**
* Returns false if this node was parsed in an inactive code branch.
* @since 5.1
*/
public boolean isActive();
/**
* Returns a copy of the tree rooted at this node.

View file

@ -23,7 +23,7 @@ import org.eclipse.core.runtime.IAdaptable;
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface IASTTranslationUnit extends IASTNode, IAdaptable {
public interface IASTTranslationUnit extends IASTNode, IASTDeclarationListOwner, IAdaptable {
/**
* <code>OWNED_DECLARATION</code> represents the relationship between an <code>IASTTranslationUnit</code> and

View file

@ -11,6 +11,7 @@
package org.eclipse.cdt.core.dom.ast.c;
import org.eclipse.cdt.core.dom.ast.IASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
/**
* Structs and Unions in C can be qualified w/restrict keyword.
@ -18,8 +19,8 @@ import org.eclipse.cdt.core.dom.ast.IASTCompositeTypeSpecifier;
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface ICASTCompositeTypeSpecifier extends
IASTCompositeTypeSpecifier, ICASTDeclSpecifier {
public interface ICASTCompositeTypeSpecifier extends IASTCompositeTypeSpecifier, ICASTDeclSpecifier,
IASTDeclarationListOwner {
/**
* @since 5.1

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -21,6 +21,20 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBas
*/
public abstract class CPPASTVisitor extends ASTVisitor implements ICPPASTVisitor {
/**
* @see ASTVisitor#ASTVisitor()
*/
public CPPASTVisitor() {
}
/**
* @see ASTVisitor#ASTVisitor(boolean)
* @since 5.1
*/
public CPPASTVisitor(boolean visitNodes) {
super(visitNodes);
}
public int visit(ICPPASTBaseSpecifier baseSpecifier) {
return PROCESS_CONTINUE;
}

View file

@ -13,6 +13,7 @@ package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNameOwner;
import org.eclipse.cdt.core.dom.ast.IASTNode;
@ -21,8 +22,8 @@ import org.eclipse.cdt.core.dom.ast.IASTNode;
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface ICPPASTCompositeTypeSpecifier extends
IASTCompositeTypeSpecifier, ICPPASTDeclSpecifier {
public interface ICPPASTCompositeTypeSpecifier extends IASTCompositeTypeSpecifier, ICPPASTDeclSpecifier,
IASTDeclarationListOwner {
/**
* <code>k_class</code> C++ introduces the class concept for composite

View file

@ -12,6 +12,7 @@ package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
/**
* This interface represents a linkage specification. e.g. extern "C" { ... }
@ -19,7 +20,7 @@ import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface ICPPASTLinkageSpecification extends IASTDeclaration {
public interface ICPPASTLinkageSpecification extends IASTDeclaration, IASTDeclarationListOwner {
/**
* Get the "literal" that represents the linkage.

View file

@ -12,17 +12,18 @@ package org.eclipse.cdt.core.dom.ast.cpp;
import org.eclipse.cdt.core.dom.ast.ASTNodeProperty;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNameOwner;
import org.eclipse.cdt.core.dom.ast.IScope;
/**
* This interface repesents a namespace definition in C++.
* This interface represents a namespace definition in C++.
*
* @noextend This interface is not intended to be extended by clients.
* @noimplement This interface is not intended to be implemented by clients.
*/
public interface ICPPASTNamespaceDefinition extends IASTDeclaration, IASTNameOwner {
public interface ICPPASTNamespaceDefinition extends IASTDeclaration, IASTNameOwner, IASTDeclarationListOwner {
/**
* <code>OWNED_DECLARATION</code> is the role served by all the nested

View file

@ -14,7 +14,26 @@ package org.eclipse.cdt.core.parser;
* @noextend This interface is not intended to be extended by clients.
* @noinstantiate This class is not intended to be instantiated by clients.
*/
public class EndOfFileException extends Exception
{
public class EndOfFileException extends Exception {
private static final long serialVersionUID= 1607883323361197919L;
private final boolean fEndsInactiveCode;
public EndOfFileException() {
fEndsInactiveCode= false;
}
/**
* @since 5.1
*/
public EndOfFileException(boolean endsInactiveCode) {
fEndsInactiveCode= true;
}
/**
* @since 5.1
*/
public boolean endsInactiveCode() {
return fEndsInactiveCode;
}
}

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.parser;
/**
* Interface for tokens of kind {@link IToken#tINACTIVE_CODE_START}, {@link IToken#tINACTIVE_CODE_SEPARATOR} and
* {@link IToken#tINACTIVE_CODE_END}.
* @since 5.1
*/
public interface IInactiveCodeToken extends IToken {
/**
* @return {@code 0} for the start-token of the outermost branch (indicates that code in the
* translation-unit outside of any branches precedes this token). <br>
* A value greater than 0 indicating how deep the code preceding this token is nested
* within code branches, otherwise.
*/
int getOldNesting();
/**
* @return {@code 0} for the end-token of the outermost branch (indicates that code in the
* translation-unit outside of any branches will follow). <br>
* A value greater than 0 indicating how deep the code following this token is nested
* within code branches, otherwise.
*/
int getNewNesting();
}

View file

@ -98,4 +98,12 @@ public interface IScanner {
* @noreference This method is not intended to be referenced by clients.
*/
public void skipInactiveCode() throws OffsetLimitReachedException;
/**
* Returns the current nesting in code branches.
* @see IInactiveCodeToken#getOldNesting()
* @see IInactiveCodeToken#getNewNesting()
* @noreference This method is not intended to be referenced by clients.
*/
public int getCodeBranchNesting();
}

View file

@ -27,10 +27,13 @@ public interface IToken {
public int getEndOffset();
public IToken getNext();
public void setNext(IToken t);
public void setType(int i);
/**
* @noreference This method is not intended to be referenced by clients.
*/
@Deprecated
public boolean isOperator();
// Token types

View file

@ -28,7 +28,6 @@ import org.eclipse.core.runtime.CoreException;
* Access to methods on scopes and bindings internal to the parser.
*/
public class ASTInternal {
public static IASTNode[] getDeclarationsOfBinding(IBinding binding) {
if( binding instanceof ICPPInternalBinding ) {
return ((ICPPInternalBinding)binding).getDeclarations();
@ -171,4 +170,16 @@ public class ASTInternal {
}
return filePath;
}
public static void addDeclaration(IBinding b, IASTNode declaration) {
if (b instanceof ICPPInternalBinding && declaration.isActive()) {
((ICPPInternalBinding) b).addDeclaration(declaration);
}
}
public static void addDefinition(IBinding b, IASTNode declaration) {
if (b instanceof ICPPInternalBinding && declaration.isActive()) {
((ICPPInternalBinding) b).addDefinition(declaration);
}
}
}

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -42,6 +42,7 @@ public abstract class ASTNode implements IASTNode {
private int offset;
private boolean frozen = false;
private boolean active = true;
public IASTNode getParent() {
return parent;
@ -56,6 +57,10 @@ public abstract class ASTNode implements IASTNode {
return frozen;
}
public boolean isActive() {
return active;
}
public void freeze() {
frozen = true;
for(IASTNode child : getChildren()) {
@ -65,6 +70,12 @@ public abstract class ASTNode implements IASTNode {
}
}
public void setInactive() {
if(frozen)
throw new IllegalStateException("attempt to modify frozen AST node"); //$NON-NLS-1$
active= false;
}
protected void assertNotFrozen() throws IllegalStateException {
if(frozen)
throw new IllegalStateException("attempt to modify frozen AST node"); //$NON-NLS-1$

View file

@ -10,19 +10,16 @@
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTArrayModifier;
import org.eclipse.cdt.core.dom.ast.IASTBinaryExpression;
import org.eclipse.cdt.core.dom.ast.IASTCastExpression;
import org.eclipse.cdt.core.dom.ast.IASTConditionalExpression;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTExpression;
import org.eclipse.cdt.core.dom.ast.IASTExpressionList;
import org.eclipse.cdt.core.dom.ast.IASTFieldDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTIdExpression;
import org.eclipse.cdt.core.dom.ast.IASTLiteralExpression;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.c.CVisitor;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
@ -30,43 +27,38 @@ import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
* Base class for {@link CVisitor} and {@link CPPVisitor}
*/
public class ASTQueries {
private static class NameSearch extends ASTVisitor {
private boolean fFound;
NameSearch() {
super(false);
shouldVisitAmbiguousNodes= true;
shouldVisitNames= true;
}
public void reset() {
fFound= false;
}
public boolean foundName() {
return fFound;
}
@Override
public int visit(IASTName name) {
fFound= true;
return PROCESS_ABORT;
}
}
private static NameSearch NAME_SEARCH= new NameSearch();
/**
* Tests whether the given expression can contain ast-names, suitable to be used before ambiguity
* resolution.
*/
public static boolean canContainName(IASTExpression expr) {
if (expr == null || expr instanceof IASTLiteralExpression)
if (expr == null)
return false;
if (expr instanceof IASTAmbiguousExpression)
return true;
if (expr instanceof IASTIdExpression)
return true;
if (expr instanceof IASTCastExpression)
return true;
if (expr instanceof IASTUnaryExpression) {
IASTUnaryExpression uexpr= (IASTUnaryExpression) expr;
return canContainName(uexpr.getOperand());
}
if (expr instanceof IASTBinaryExpression) {
IASTBinaryExpression bexpr= (IASTBinaryExpression) expr;
return canContainName(bexpr.getOperand1()) || canContainName(bexpr.getOperand2());
}
if (expr instanceof IASTConditionalExpression) {
IASTConditionalExpression cexpr= (IASTConditionalExpression) expr;
return canContainName(cexpr.getLogicalConditionExpression()) ||
canContainName(cexpr.getPositiveResultExpression()) || canContainName(cexpr.getNegativeResultExpression());
}
if (expr instanceof IASTExpressionList) {
IASTExpressionList lexpr= (IASTExpressionList) expr;
IASTExpression[] subexprs= lexpr.getExpressions();
for (IASTExpression subexpr : subexprs) {
if (canContainName(subexpr))
return true;
}
}
return true;
NAME_SEARCH.reset();
expr.accept(NAME_SEARCH);
return NAME_SEARCH.foundName();
}
/**
@ -114,4 +106,25 @@ public class ASTQueries {
}
return result;
}
/**
* Extracts the active declarations from an array of declarations.
*/
public static IASTDeclaration[] extractActiveDeclarations(final IASTDeclaration[] allDeclarations, final int size) {
IASTDeclaration[] active;
if (size == 0) {
active= IASTDeclaration.EMPTY_DECLARATION_ARRAY;
} else {
active= new IASTDeclaration[size];
int j= 0;
for (int i = 0; i < size; i++) {
IASTDeclaration d= allDeclarations[i];
if (d.isActive()) {
active[j++]= d;
}
}
active= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, active, j-1);
}
return active;
}
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2008 Wind River Systems, Inc. and others.
* Copyright (c) 2008, 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
@ -16,7 +16,6 @@ import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.dom.IName;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTComment;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTFileLocation;
import org.eclipse.cdt.core.dom.ast.IASTName;
@ -36,7 +35,6 @@ import org.eclipse.cdt.core.index.IIndex;
import org.eclipse.cdt.core.index.IIndexFile;
import org.eclipse.cdt.core.index.IIndexFileSet;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.cpp.CPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.internal.core.parser.scanner.ILocationResolver;
import org.eclipse.cdt.internal.core.parser.scanner.ISkippedIndexedFilesListener;
import org.eclipse.cdt.internal.core.parser.scanner.IncludeFileContent;
@ -54,8 +52,9 @@ public abstract class ASTTranslationUnit extends ASTNode implements IASTTranslat
private static final IASTProblem[] EMPTY_PROBLEM_ARRAY = new IASTProblem[0];
private static final String EMPTY_STRING = ""; //$NON-NLS-1$
protected IASTDeclaration[] fDeclarations = null;
protected int fLastDeclaration=-1;
private IASTDeclaration[] fAllDeclarations = null;
private IASTDeclaration[] fActiveDeclarations= null;
private int fLastDeclaration=-1;
protected ILocationResolver fLocationResolver;
private IIndex fIndex;
@ -73,19 +72,39 @@ public abstract class ASTTranslationUnit extends ASTNode implements IASTTranslat
if (d != null) {
d.setParent(this);
d.setPropertyInParent(OWNED_DECLARATION);
fDeclarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, fDeclarations, ++fLastDeclaration, d);
fAllDeclarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, fAllDeclarations, ++fLastDeclaration, d);
fActiveDeclarations= null;
}
}
/*
* (non-Javadoc)
*
* @see org.eclipse.cdt.core.dom.ast.IASTTranslationUnit#getDeclarations()
*/
public final IASTDeclaration[] getDeclarations() {
if (fDeclarations == null) return IASTDeclaration.EMPTY_DECLARATION_ARRAY;
fDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter( IASTDeclaration.class, fDeclarations, fLastDeclaration);
return fDeclarations;
IASTDeclaration[] active= fActiveDeclarations;
if (active == null) {
active = ASTQueries.extractActiveDeclarations(fAllDeclarations, fLastDeclaration+1);
fActiveDeclarations= active;
}
return active;
}
public final IASTDeclaration[] getDeclarations(boolean includeInactive) {
if (includeInactive) {
fAllDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, fAllDeclarations, fLastDeclaration);
return fAllDeclarations;
}
return getDeclarations();
}
public final void replace(IASTNode child, IASTNode other) {
assert child.isActive() == other.isActive();
for (int i = 0; i <= fLastDeclaration; ++i) {
if (fAllDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fAllDeclarations[i] = (IASTDeclaration) other;
fActiveDeclarations= null;
return;
}
}
}
/*
@ -235,24 +254,21 @@ public abstract class ASTTranslationUnit extends ASTNode implements IASTTranslat
@Override
public final boolean accept( ASTVisitor action ){
if( action.shouldVisitTranslationUnit){
switch( action.visit( this ) ){
if (action.shouldVisitTranslationUnit) {
switch (action.visit(this)) {
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
}
IASTDeclaration [] ds = getDeclarations();
for( int i = 0; i < ds.length; i++ ){
if( !ds[i].accept( action ) ) return false;
}
if( action.shouldVisitTranslationUnit){
switch( action.leave( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
IASTDeclaration[] decls = getDeclarations(action.includeInactiveNodes);
for (IASTDeclaration decl : decls) {
if (!decl.accept(action)) return false;
}
if (action.shouldVisitTranslationUnit && action.leave(this) == ASTVisitor.PROCESS_ABORT)
return false;
return true;
}
@ -354,35 +370,7 @@ public abstract class ASTTranslationUnit extends ASTNode implements IASTTranslat
/**
* Must be called by the parser, before the ast is passed to the clients.
*/
public void resolveAmbiguities() {
accept(createAmbiguityNodeVisitor());
cleanupAfterAmbiguityResolution();
}
protected abstract ASTVisitor createAmbiguityNodeVisitor();
protected void cleanupAfterAmbiguityResolution() {
// clear bindings (see bug 232811)
accept(new ASTVisitor(){
{
shouldVisitNames= true;
shouldVisitDeclSpecifiers= true;
}
@Override
public int visit(IASTName name) {
name.setBinding(null);
return PROCESS_CONTINUE;
}
@Override
public int visit(IASTDeclSpecifier declSpec) {
if (declSpec instanceof CPPASTCompositeTypeSpecifier)
((CPPASTCompositeTypeSpecifier) declSpec).setScope(null);
return PROCESS_CONTINUE;
}
});
}
public abstract void resolveAmbiguities();
protected void copyAbstractTU(ASTTranslationUnit copy) {
copy.setIndex(fIndex);

View file

@ -14,6 +14,7 @@
package org.eclipse.cdt.internal.core.dom.parser;
import org.eclipse.cdt.core.dom.ast.ASTCompletionNode;
import org.eclipse.cdt.core.dom.ast.ASTGenericVisitor;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.IASTASMDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTArrayDeclarator;
@ -22,11 +23,13 @@ import org.eclipse.cdt.core.dom.ast.IASTBreakStatement;
import org.eclipse.cdt.core.dom.ast.IASTCaseStatement;
import org.eclipse.cdt.core.dom.ast.IASTCastExpression;
import org.eclipse.cdt.core.dom.ast.IASTCompletionNode;
import org.eclipse.cdt.core.dom.ast.IASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTCompoundStatement;
import org.eclipse.cdt.core.dom.ast.IASTConditionalExpression;
import org.eclipse.cdt.core.dom.ast.IASTContinueStatement;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationListOwner;
import org.eclipse.cdt.core.dom.ast.IASTDeclarationStatement;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
import org.eclipse.cdt.core.dom.ast.IASTDefaultStatement;
@ -70,6 +73,7 @@ import org.eclipse.cdt.core.dom.parser.ISourceCodeParser;
import org.eclipse.cdt.core.parser.AbstractParserLogService;
import org.eclipse.cdt.core.parser.EndOfFileException;
import org.eclipse.cdt.core.parser.IGCCToken;
import org.eclipse.cdt.core.parser.IInactiveCodeToken;
import org.eclipse.cdt.core.parser.IParserLogService;
import org.eclipse.cdt.core.parser.IProblem;
import org.eclipse.cdt.core.parser.IScanner;
@ -108,6 +112,17 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
}
}
private static final ASTVisitor MARK_INACTIVE = new ASTGenericVisitor(true) {
{
shouldVisitAmbiguousNodes= true;
}
@Override
protected int genericVisit(IASTNode node) {
((ASTNode) node).setInactive();
return PROCESS_CONTINUE;
}
};
protected static final int DEFAULT_DESIGNATOR_LIST_SIZE = 4;
protected static int parseCount = 0;
@ -135,8 +150,8 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
* enter a nested declaration, in order to avoid holding on to all the tokens.
*/
protected IToken declarationMark;
protected IToken currToken;
protected int eofOffset;
protected IToken nextToken;
protected IToken lastTokenFromScanner;
protected boolean onTopInTemplateArgs= false;
protected boolean inBinaryExpression= true;
@ -149,6 +164,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
protected IASTTypeId fTypeIdForCastAmbiguity;
private final INodeFactory nodeFactory;
private boolean fActiveCode= true;
protected AbstractGNUSourceCodeParser(IScanner scanner,
IParserLogService logService, ParserMode parserMode,
@ -206,43 +222,179 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
}
/**
* Returns the next token without advancing
* Fetches the next token from the scanner.
*/
protected IToken mark() throws EndOfFileException {
return currToken == null ? currToken = fetchToken(true) : currToken;
private final IToken fetchToken(boolean skipInactive) throws EndOfFileException {
try {
IToken t= scanner.nextToken();
if (skipInactive) {
while (t.getType() == IToken.tINACTIVE_CODE_START) {
scanner.skipInactiveCode();
t= scanner.nextToken();
}
}
if (lastTokenFromScanner != null)
lastTokenFromScanner.setNext(t);
lastTokenFromScanner= t;
return t;
} catch (OffsetLimitReachedException olre) {
if (mode != ParserMode.COMPLETION_PARSE)
throw new EndOfFileException();
createCompletionNode(olre.getFinalToken());
throw olre;
}
}
private final IToken nextToken(boolean skipInactive) throws EndOfFileException {
IToken t= nextToken;
if (t == null) {
t= fetchToken(skipInactive);
}
nextToken= t;
return t;
}
private final IToken lookaheadToken(int i, boolean skipInactive) throws EndOfFileException {
assert i >= 0;
if (isCancelled) {
throw new ParseError(ParseError.ParseErrorKind.TIMEOUT_OR_CANCELLED);
}
IToken t= nextToken(skipInactive);
for (; i > 1; --i) {
t = t.getNext();
if (t == null)
t = fetchToken(skipInactive);
}
return t;
}
/**
* Returns the next token without advancing. Same as {@code LA(1)}.
*/
protected final IToken LA() throws EndOfFileException {
IToken t= nextToken(true);
checkForEOI(t);
return t;
}
/**
* Returns one of the next tokens. With {@code i == 1}, the next token is returned.
* @param i number of tokens to look ahead, must be greater than 0.
*/
protected final IToken LA(int i) throws EndOfFileException {
IToken t= lookaheadToken(i, true);
checkForEOI(t);
return t;
}
/**
* Consumes and returns the next token available.
*/
protected final IToken consume() throws EndOfFileException {
IToken t= nextToken(true);
checkForEOI(t);
nextToken= t.getNext();
return t;
}
/**
* Tests whether we are looking at a change from active to inactive code at this point. If so, the change
* is accepted.
*
* @param nesting
* the nesting level of the code branch we have to stay within
* @return <code>false</code> if an inactive code branch was rejected because of its nesting level,
* <code>true</code>, otherwise.
*/
protected final boolean acceptInactiveCodeBoundary(int nesting) {
try {
while (true) {
IToken t= nextToken(false);
switch (t.getType()) {
case IToken.tINACTIVE_CODE_START:
case IToken.tINACTIVE_CODE_SEPARATOR:
IInactiveCodeToken it = (IInactiveCodeToken) t;
if (it.getNewNesting() < nesting || (it.getNewNesting() == nesting && it.getOldNesting() == nesting)) {
return false;
}
fActiveCode= false;
nextToken= t.getNext(); // consume the token
continue;
case IToken.tINACTIVE_CODE_END:
it = (IInactiveCodeToken) t;
if (it.getNewNesting() < nesting || (it.getNewNesting() == nesting && it.getOldNesting() == nesting)) {
return false;
}
fActiveCode= true;
nextToken= t.getNext(); // consume the token
continue;
default:
return true;
}
}
} catch (EndOfFileException e) {
}
return true;
}
protected final void skipInactiveCode() throws OffsetLimitReachedException {
IToken t= nextToken;
if (fActiveCode && (t == null || t.getType() != IToken.tINACTIVE_CODE_START))
return;
try {
fActiveCode= true;
while (t != null && t.getType() != IToken.tINACTIVE_CODE_END)
t= t.getNext();
if (t != null) {
nextToken= t.getNext();
} else {
nextToken= null;
scanner.skipInactiveCode();
}
} catch (OffsetLimitReachedException olre) {
if (mode == ParserMode.COMPLETION_PARSE) {
createCompletionNode(olre.getFinalToken());
throw olre;
}
}
}
protected final boolean isActiveCode() {
return fActiveCode;
}
protected final int getCodeBranchNesting() {
return scanner.getCodeBranchNesting();
}
/**
* Returns the next token, which can be used to reset the input back to
* this point in the stream.
*/
protected final IToken mark() throws EndOfFileException {
return LA();
}
/**
* Roll back to a previous point, reseting the queue of tokens.
* @param mark a token previously obtained via {@link #mark()}.
*/
protected void backup(IToken mark) {
currToken = mark;
protected final void backup(IToken mark) {
nextToken = mark;
}
/**
* Look ahead in the token list to see what is coming.
* @param i number of tokens to look ahead, must be greater or equal to 0.
* @return the token you wish to observe
*/
protected IToken LA(int i) throws EndOfFileException {
assert i >= 0;
if (isCancelled) {
throw new ParseError(ParseError.ParseErrorKind.TIMEOUT_OR_CANCELLED);
}
IToken retToken= mark();
for (; i > 1; --i) {
retToken = retToken.getNext();
if (retToken == null)
retToken = fetchToken(true);
}
return retToken;
private final void checkForEOI(IToken t) throws EndOfFileException {
final int lt= t.getType();
if (lt == IToken.tINACTIVE_CODE_SEPARATOR || lt == IToken.tINACTIVE_CODE_END)
throw new EndOfFileException(true);
}
/**
* Same as {@link #LA(int)}, but returns <code>null</code> when eof is reached.
*/
protected IToken LAcatchEOF(int i) {
protected final IToken LAcatchEOF(int i) {
try {
return LA(i);
} catch (EndOfFileException e) {
@ -255,14 +407,14 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
* @param i number of tokens to look ahead, must be greater or equal to 0.
* @return The type of that token
*/
protected int LT(int i) throws EndOfFileException {
protected final int LT(int i) throws EndOfFileException {
return LA(i).getType();
}
/**
* Same as {@link #LT(int)}, but returns <code>0</code> when eof is reached.
*/
protected int LTcatchEOF(int i) {
protected final int LTcatchEOF(int i) {
try {
return LT(i);
} catch (EndOfFileException e) {
@ -270,52 +422,12 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
}
}
protected boolean isOnSameLine(int offset1, int offset2) {
ILocationResolver lr= (ILocationResolver) getTranslationUnit().getAdapter(ILocationResolver.class);
IASTFileLocation floc= lr.getMappedFileLocation(offset1, offset2-offset1+1);
return floc.getFileName().equals(lr.getContainingFilePath(offset1)) &&
floc.getStartingLineNumber() == floc.getEndingLineNumber();
}
protected int calculateEndOffset(IASTNode n) {
ASTNode node = (ASTNode) n;
return node.getOffset() + node.getLength();
}
protected void setRange(IASTNode n, IASTNode from) {
((ASTNode) n).setOffsetAndLength((ASTNode) from);
}
protected void setRange(IASTNode n, int offset, int endOffset) {
((ASTNode) n).setOffsetAndLength(offset, endOffset-offset);
}
protected void adjustLength(IASTNode n, IASTNode endNode) {
final int endOffset= calculateEndOffset(endNode);
final ASTNode node = (ASTNode) n;
node.setLength(endOffset-node.getOffset());
}
/**
* Consume the next token available, regardless of the type and returns it.
*
* @return The token that was consumed and removed from our buffer.
* @throws EndOfFileException
* If there is no token to consume.
*/
protected IToken consume() throws EndOfFileException {
final IToken result= mark();
currToken= result.getNext();
return result;
}
/**
* If the type of the next token matches, it is consumed and returned. Otherwise a
* {@link BacktrackException} will be thrown.
*
* @param type the expected type of the next token.
*/
protected IToken consume(int type) throws EndOfFileException, BacktrackException {
protected final IToken consume(int type) throws EndOfFileException, BacktrackException {
final IToken result= consume();
if (result.getType() != type)
throwBacktrack(result);
@ -323,14 +435,14 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
}
/**
* Consume the next token available only if the type is as specified. In case we
* reached the end of completion, no token is consumed and the eoc-token returned.
* Consume the next token available only if the type is as specified. In case we reached the end of
* completion, no token is consumed and the eoc-token returned.
*
* @param type
* The type of token that you are expecting.
* @return the token that was consumed and removed from our buffer.
* @throws BacktrackException
* If LT(1) != type
* if LT(1) != type
*/
protected IToken consumeOrEOC(int type) throws EndOfFileException, BacktrackException {
final IToken la1= LA(1);
@ -343,30 +455,36 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
return consume();
}
/**
* Fetches the next token from the scanner.
*/
private IToken fetchToken(boolean skipInactive) throws EndOfFileException {
try {
IToken result= scanner.nextToken();
while (result.getType() == IToken.tINACTIVE_CODE_START) {
scanner.skipInactiveCode();
result= scanner.nextToken();
}
eofOffset= result.getEndOffset();
return result;
} catch (OffsetLimitReachedException olre) {
handleOffsetLimitException(olre);
// never returns, to make the java-compiler happy:
return null;
}
protected final boolean isOnSameLine(int offset1, int offset2) {
ILocationResolver lr= (ILocationResolver) getTranslationUnit().getAdapter(ILocationResolver.class);
IASTFileLocation floc= lr.getMappedFileLocation(offset1, offset2-offset1+1);
return floc.getFileName().equals(lr.getContainingFilePath(offset1)) &&
floc.getStartingLineNumber() == floc.getEndingLineNumber();
}
protected void handleOffsetLimitException(OffsetLimitReachedException exception) throws EndOfFileException {
if (mode != ParserMode.COMPLETION_PARSE)
throw new EndOfFileException();
createCompletionNode(exception.getFinalToken());
throw exception;
protected final int calculateEndOffset(IASTNode n) {
ASTNode node = (ASTNode) n;
return node.getOffset() + node.getLength();
}
protected final void setRange(IASTNode n, IASTNode from) {
((ASTNode) n).setOffsetAndLength((ASTNode) from);
}
protected final void setRange(IASTNode n, int offset, int endOffset) {
((ASTNode) n).setOffsetAndLength(offset, endOffset-offset);
}
protected final void adjustLength(IASTNode n, IASTNode endNode) {
final int endOffset= calculateEndOffset(endNode);
final ASTNode node = (ASTNode) n;
node.setLength(endOffset-node.getOffset());
}
protected final int getEndOffset() {
if (lastTokenFromScanner == null)
return 0;
return lastTokenFromScanner.getEndOffset();
}
/**
@ -487,13 +605,23 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
protected abstract void nullifyTranslationUnit();
protected IToken skipOverCompoundStatement() throws BacktrackException,
EndOfFileException {
protected IToken skipOverCompoundStatement() throws BacktrackException, EndOfFileException {
// speed up the parser by skipping the body, simply look for matching brace and return
final boolean isActive = isActiveCode();
final int codeBranchNesting= getCodeBranchNesting();
consume(IToken.tLBRACE);
IToken result = null;
int depth = 1;
while (depth > 0) {
if (!isActive) {
IToken t= lookaheadToken(1, false);
final int lt= t.getType();
if (lt == IToken.tINACTIVE_CODE_SEPARATOR || lt == IToken.tINACTIVE_CODE_END || lt == IToken.tINACTIVE_CODE_START) {
if (!acceptInactiveCodeBoundary(codeBranchNesting))
throw new EndOfFileException(true);
}
}
result = consume();
switch (result.getType()) {
case IToken.tRBRACE:
@ -541,7 +669,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
while(true) {
switch (LT(1)) {
case IToken.tEOC:
endOffset= eofOffset;
endOffset= getEndOffset();
break loop;
case IToken.tSEMI:
if (depth == 0) {
@ -567,7 +695,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
endOffset= consume().getEndOffset();
}
} catch (EndOfFileException e) {
endOffset= eofOffset;
endOffset= getEndOffset();
}
return endOffset;
}
@ -581,7 +709,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
while(true) {
switch (LT(1)) {
case IToken.tEOC:
endOffset= eofOffset;
endOffset= getEndOffset();
break loop;
case IToken.tSEMI:
case IToken.tLBRACE:
@ -610,7 +738,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
endOffset= consume().getEndOffset();
}
} catch (EndOfFileException e) {
endOffset= eofOffset;
endOffset= getEndOffset();
}
IASTProblem problem= createProblem(IProblem.SYNTAX_ERROR, offset, endOffset-offset);
return buildProblemExpression(problem);
@ -698,7 +826,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
protected IASTExpression compoundStatementExpression() throws EndOfFileException, BacktrackException {
int startingOffset = consume().getOffset(); // tLPAREN always
IASTCompoundStatement compoundStatement = null;
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE)
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE || !isActiveCode())
skipOverCompoundStatement();
else if (mode == ParserMode.COMPLETION_PARSE || mode == ParserMode.SELECTION_PARSE) {
if (scanner.isOnTopContext())
@ -863,44 +991,94 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
protected void parseTranslationUnit() {
final IASTTranslationUnit tu= getTranslationUnit();
int offset= -1;
declarationList(tu, DeclarationOptions.GLOBAL, false, 0);
((ASTNode) tu).setLength(getEndOffset());
}
protected final void declarationListInBraces(final IASTDeclarationListOwner tu, int offset, DeclarationOptions options) throws EndOfFileException, BacktrackException {
// consume brace, if requested
int codeBranchNesting= getCodeBranchNesting();
consume(IToken.tLBRACE);
declarationList(tu, options, true, codeBranchNesting);
final int lt1 = LTcatchEOF(1);
if (lt1 == IToken.tRBRACE) {
int endOffset= consume().getEndOffset();
setRange(tu, offset, endOffset);
return;
}
final int endOffset = getEndOffset();
setRange(tu, offset, endOffset);
if (lt1 == IToken.tEOC || (lt1 == 0 && tu instanceof IASTCompositeTypeSpecifier)) {
return;
}
throwBacktrack(createProblem(IProblem.SYNTAX_ERROR, endOffset, 0), tu);
}
private final void declarationList(final IASTDeclarationListOwner tu, DeclarationOptions options, boolean upToBrace, int codeBranchNesting) {
final boolean wasActive= isActiveCode();
while (true) {
final boolean ok= acceptInactiveCodeBoundary(codeBranchNesting);
if (!ok) {
// we left to an enclosing code branch. If we started in inactive code, it's time to leave.
if (!wasActive)
return;
// if we started in active code, we need to skip the outer and therefore unrelated
// inactive branches until we hit active code again.
try {
skipInactiveCode();
} catch (OffsetLimitReachedException e) {
return;
}
codeBranchNesting= Math.min(getCodeBranchNesting()+1, codeBranchNesting);
// we could be at the start of inactive code so restart the loop
continue;
}
final boolean active= isActiveCode();
IToken next= LAcatchEOF(1);
if (next == null || next.getType() == IToken.tEOC)
break;
return;
final int nextOffset = next.getOffset();
if (upToBrace && next.getType() == IToken.tRBRACE && active == wasActive) {
return;
}
final int offset = next.getOffset();
declarationMark= next;
next= null; // don't hold on to the token while parsing namespaces, class bodies, etc.
if (offset == nextOffset) {
// no progress
tu.addDeclaration(skipProblemDeclaration(offset));
} else {
offset= nextOffset;
final IASTDeclaration declaration= declaration(DeclarationOptions.GLOBAL);
tu.addDeclaration(declaration);
try {
IASTDeclaration declaration= declaration(options);
if (((ASTNode) declaration).getLength() == 0 && LTcatchEOF(1) != IToken.tEOC) {
declaration= skipProblemDeclaration(offset);
}
addDeclaration(tu, declaration, active);
} catch (BacktrackException bt) {
IASTDeclaration[] decls= problemDeclaration(offset, bt, DeclarationOptions.GLOBAL);
IASTDeclaration[] decls= problemDeclaration(offset, bt, options);
for (IASTDeclaration declaration : decls) {
tu.addDeclaration(declaration);
addDeclaration(tu, declaration, active);
}
} catch (EndOfFileException e) {
tu.addDeclaration(skipProblemDeclaration(offset));
IASTDeclaration declaration= skipProblemDeclaration(offset);
addDeclaration(tu, declaration, active);
if (!e.endsInactiveCode()) {
break;
} catch (OutOfMemoryError oome) {
logThrowable("translationUnit", oome); //$NON-NLS-1$
throw oome;
} catch (Exception e) {
logException("translationUnit", e); //$NON-NLS-1$
tu.addDeclaration(skipProblemDeclaration(offset));
}
} finally {
declarationMark= null;
}
}
((ASTNode) tu).setLength(eofOffset);
}
private void addDeclaration(final IASTDeclarationListOwner parent, IASTDeclaration declaration,
final boolean active) {
if (!active) {
declaration.accept(MARK_INACTIVE);
}
parent.addDeclaration(declaration);
}
protected IASTExpression assignmentOperatorExpression(int kind,
@ -1162,19 +1340,19 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
protected IASTStatement handleFunctionBody() throws BacktrackException, EndOfFileException {
declarationMark= null;
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE) {
IToken curr = LA(1);
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE || !isActiveCode()) {
int offset = LA(1).getOffset();
IToken last = skipOverCompoundStatement();
IASTCompoundStatement cs = nodeFactory.newCompoundStatement();
((ASTNode) cs).setOffsetAndLength(curr.getOffset(), last.getEndOffset() - curr.getOffset());
setRange(cs, offset, last.getEndOffset());
return cs;
} else if (mode == ParserMode.COMPLETION_PARSE || mode == ParserMode.SELECTION_PARSE) {
if (scanner.isOnTopContext())
return functionBody();
IToken curr = LA(1);
int offset = LA(1).getOffset();
IToken last = skipOverCompoundStatement();
IASTCompoundStatement cs = nodeFactory.newCompoundStatement();
((ASTNode) cs).setOffsetAndLength(curr.getOffset(), last.getEndOffset() - curr.getOffset());
setRange(cs, offset, last.getEndOffset());
return cs;
}
@ -1261,7 +1439,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
loop: while (true) {
switch (LTcatchEOF(1)) {
case 0: // eof
endOffset= eofOffset;
endOffset= getEndOffset();
break loop;
case IToken.tRBRACE:
endOffset= consume().getEndOffset();
@ -1302,7 +1480,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
}
}
} catch (EndOfFileException eof) {
throwBacktrack(createProblem(IProblem.SYNTAX_ERROR, problemOffset, eofOffset-problemOffset), result);
throwBacktrack(createProblem(IProblem.SYNTAX_ERROR, problemOffset, getEndOffset()-problemOffset), result);
} catch (BacktrackException bt) {
IASTProblem problem= skipProblemEnumerator(problemOffset);
throwBacktrack(problem, result);
@ -1352,7 +1530,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
return new IASTDeclaration[] {(IASTDeclaration) n, buildProblemDeclaration(origProblem)};
}
if (declarationMark != null) {
if (declarationMark != null && isActiveCode()) {
IASTDeclaration trailingProblem= null;
offset= declarationMark.getOffset();
@ -1382,7 +1560,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
break;
}
} catch (EndOfFileException e) {
endOffset= eofOffset;
endOffset= getEndOffset();
break;
}
}
@ -1995,10 +2173,10 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
*/
protected void __attribute_decl_seq(boolean allowAttrib, boolean allowDeclspec) throws BacktrackException, EndOfFileException {
while (true) {
IToken token = LA(1);
if ( allowAttrib && (token.getType() == IGCCToken.t__attribute__)) {
final int lt = LTcatchEOF(1);
if ( allowAttrib && (lt == IGCCToken.t__attribute__)) {
__attribute__();
} else if (allowDeclspec && (token.getType() == IGCCToken.t__declspec)) {
} else if (allowDeclspec && (lt == IGCCToken.t__declspec)) {
__declspec();
} else {
break;

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2008 Wind River Systems, Inc. and others.
* Copyright (c) 2008, 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
@ -10,59 +10,31 @@
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser;
import org.eclipse.cdt.core.dom.ast.IASTArrayModifier;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.ASTGenericVisitor;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
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.IASTNode;
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
import org.eclipse.cdt.core.dom.ast.IASTProblem;
import org.eclipse.cdt.core.dom.ast.IASTStatement;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
import org.eclipse.cdt.core.dom.ast.IASTTypeId;
import org.eclipse.cdt.core.dom.ast.IASTEnumerationSpecifier.IASTEnumerator;
import org.eclipse.cdt.core.dom.ast.c.ICASTDesignator;
import org.eclipse.cdt.core.dom.ast.c.ICASTVisitor;
import org.eclipse.cdt.core.dom.ast.cpp.CPPASTVisitor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTNamespaceDefinition;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTemplateParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier;
/**
* Visitor to search for nodes by file offsets.
* @since 5.0
*/
public class FindNodeForOffsetAction extends CPPASTVisitor implements ICASTVisitor {
public class FindNodeForOffsetAction extends ASTGenericVisitor {
private final ASTNodeSpecification<?> fNodeSpec;
public FindNodeForOffsetAction(ASTNodeSpecification<?> nodeSpec) {
super(!nodeSpec.requiresClass(IASTName.class));
fNodeSpec= nodeSpec;
shouldVisitNames = true;
shouldVisitDeclarations= true;
shouldVisitArrayModifiers=
shouldVisitInitializers=
shouldVisitParameterDeclarations=
shouldVisitDeclarators=
shouldVisitDeclSpecifiers=
shouldVisitDesignators=
shouldVisitEnumerators=
shouldVisitExpressions=
shouldVisitStatements=
shouldVisitTypeIds=
shouldVisitEnumerators=
shouldVisitBaseSpecifiers=
shouldVisitNamespaces=
shouldVisitTemplateParameters=
shouldVisitTranslationUnit= !nodeSpec.requiresClass(IASTName.class);
includeInactiveNodes= true;
}
public int processNode(IASTNode node) {
@Override
public int genericVisit(IASTNode node) {
if (node instanceof ASTNode) {
final ASTNode astNode = (ASTNode) node;
if (!fNodeSpec.canContainMatches(astNode)) {
@ -80,96 +52,17 @@ public class FindNodeForOffsetAction extends CPPASTVisitor implements ICASTVisit
if (declaration instanceof ASTNode && ((ASTNode) declaration).getOffset() > fNodeSpec.getSequenceEnd())
return PROCESS_ABORT;
return processNode(declaration);
return genericVisit(declaration);
}
@Override
public int visit(IASTDeclarator declarator) {
int ret = processNode(declarator);
int ret = genericVisit(declarator);
IASTPointerOperator[] ops = declarator.getPointerOperators();
for (int i = 0; i < ops.length; i++)
processNode(ops[i]);
genericVisit(ops[i]);
return ret;
}
@Override
public int visit(IASTArrayModifier arrayModifier) {
return processNode(arrayModifier);
}
@Override
public int visit(IASTDeclSpecifier declSpec) {
return processNode(declSpec);
}
@Override
public int visit(IASTEnumerator enumerator) {
return processNode(enumerator);
}
@Override
public int visit(IASTExpression expression) {
return processNode(expression);
}
@Override
public int visit(IASTInitializer initializer) {
return processNode(initializer);
}
@Override
public int visit(IASTName name) {
return processNode(name);
}
@Override
public int visit(IASTParameterDeclaration parameterDeclaration) {
return processNode(parameterDeclaration);
}
@Override
public int visit(IASTStatement statement) {
return processNode(statement);
}
@Override
public int visit(IASTTypeId typeId) {
return processNode(typeId);
}
@Override
public int visit(ICPPASTBaseSpecifier baseSpecifier) {
return processNode(baseSpecifier);
}
@Override
public int visit(ICPPASTNamespaceDefinition namespaceDefinition) {
return processNode(namespaceDefinition);
}
@Override
public int visit(ICPPASTTemplateParameter templateParameter) {
return processNode(templateParameter);
}
@Override
public int visit(IASTProblem problem) {
return processNode(problem);
}
public int visit(ICASTDesignator designator) {
return processNode(designator);
}
public int leave(ICASTDesignator designator) {
return PROCESS_CONTINUE;
}
@Override
public int visit(IASTTranslationUnit tu) {
return processNode(tu);
}
}

View file

@ -28,6 +28,7 @@ import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode;
public final class CASTAmbiguityResolver extends ASTVisitor {
public CASTAmbiguityResolver() {
super(false);
includeInactiveNodes= true;
shouldVisitAmbiguousNodes= true;
}

View file

@ -19,6 +19,7 @@ import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.c.ICASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/**
@ -27,15 +28,18 @@ import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
public class CASTCompositeTypeSpecifier extends CASTBaseDeclSpecifier implements
ICASTCompositeTypeSpecifier, IASTAmbiguityParent {
private int key;
private IASTName name;
private int fKey;
private IASTName fName;
private IASTDeclaration[] fActiveDeclarations= null;
private IASTDeclaration [] fAllDeclarations = null;
private int fDeclarationsPos=-1;
private IScope fScope = null;
public CASTCompositeTypeSpecifier() {
}
public CASTCompositeTypeSpecifier(int key, IASTName name) {
this.key = key;
this.fKey = key;
setName(name);
}
@ -47,106 +51,115 @@ public class CASTCompositeTypeSpecifier extends CASTBaseDeclSpecifier implements
protected void copyCompositeTypeSpecifier(CASTCompositeTypeSpecifier copy) {
copyBaseDeclSpec(copy);
copy.setKey(key);
copy.setName(name == null ? null : name.copy());
copy.setKey(fKey);
copy.setName(fName == null ? null : fName.copy());
for(IASTDeclaration member : getMembers())
copy.addMemberDeclaration(member == null ? null : member.copy());
}
public int getKey() {
return key;
return fKey;
}
public void setKey(int key) {
assertNotFrozen();
this.key = key;
this.fKey = key;
}
public IASTName getName() {
return name;
return fName;
}
public void setName(IASTName name) {
assertNotFrozen();
this.name = name;
this.fName = name;
if (name != null) {
name.setParent(this);
name.setPropertyInParent(TYPE_NAME);
}
}
private IASTDeclaration [] declarations = null;
private int declarationsPos=-1;
private IScope scope = null;
public IASTDeclaration [] getMembers() {
if( declarations == null ) return IASTDeclaration.EMPTY_DECLARATION_ARRAY;
declarations = (IASTDeclaration[]) ArrayUtil.removeNullsAfter( IASTDeclaration.class, declarations, declarationsPos );
return declarations;
public IASTDeclaration[] getMembers() {
IASTDeclaration[] active= fActiveDeclarations;
if (active == null) {
active = ASTQueries.extractActiveDeclarations(fAllDeclarations, fDeclarationsPos+1);
fActiveDeclarations= active;
}
return active;
}
public final IASTDeclaration[] getDeclarations(boolean includeInactive) {
if (includeInactive) {
fAllDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, fAllDeclarations, fDeclarationsPos);
return fAllDeclarations;
}
return getMembers();
}
public void addMemberDeclaration(IASTDeclaration declaration) {
assertNotFrozen();
if (declaration != null) {
declaration.setParent(this);
declaration.setPropertyInParent(MEMBER_DECLARATION);
declarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, declarations, ++declarationsPos, declaration );
fAllDeclarations = (IASTDeclaration[]) ArrayUtil.append(IASTDeclaration.class, fAllDeclarations,
++fDeclarationsPos, declaration);
fActiveDeclarations= null;
}
}
public void addDeclaration(IASTDeclaration declaration) {
addMemberDeclaration(declaration);
}
public IScope getScope() {
if( scope == null )
scope = new CCompositeTypeScope( this );
return scope;
if( fScope == null )
fScope = new CCompositeTypeScope( this );
return fScope;
}
@Override
public boolean accept( ASTVisitor action ){
if( action.shouldVisitDeclSpecifiers ){
switch( action.visit( this ) ){
if (action.shouldVisitDeclSpecifiers) {
switch (action.visit(this)) {
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
}
if( name != null ) if( !name.accept( action ) ) return false;
if (fName != null && !fName.accept(action))
return false;
IASTDeclaration [] decls = getMembers();
for( int i = 0; i < decls.length; i++ )
if( !decls[i].accept( action ) ) return false;
IASTDeclaration[] decls= getDeclarations(action.includeInactiveNodes);
for (int i = 0; i < decls.length; i++) {
if (!decls[i].accept(action)) return false;
}
if( action.shouldVisitDeclSpecifiers ){
switch( action.leave( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
if (action.shouldVisitDeclSpecifiers) {
switch (action.leave(this)) {
case ASTVisitor.PROCESS_ABORT: return false;
case ASTVisitor.PROCESS_SKIP: return true;
default: break;
}
}
return true;
}
public int getRoleForName(IASTName n) {
if( n == this.name )
if( n == this.fName )
return r_definition;
return r_unclear;
}
public void replace(IASTNode child, IASTNode other) {
if (declarations == null) return;
for(int i=0; i < declarations.length; ++i) {
if (declarations[i] == null) break;
if (declarations[i] == child) {
assert child.isActive() == other.isActive();
for (int i = 0; i <= fDeclarationsPos; ++i) {
if (fAllDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
declarations[i] = (IASTDeclaration) other;
break;
fAllDeclarations[i] = (IASTDeclaration) other;
fActiveDeclarations= null;
return;
}
}
}
}

View file

@ -14,11 +14,8 @@ package org.eclipse.cdt.internal.core.dom.parser.c;
import org.eclipse.cdt.core.dom.ILinkage;
import org.eclipse.cdt.core.dom.IName;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.EScopeKind;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.ICompositeType;
import org.eclipse.cdt.core.dom.ast.IMacroBinding;
@ -99,21 +96,8 @@ public class CASTTranslationUnit extends ASTTranslationUnit implements IASTAmbig
}
@Override
protected ASTVisitor createAmbiguityNodeVisitor() {
return new CASTAmbiguityResolver();
}
public void replace(IASTNode child, IASTNode other) {
if (fDeclarations == null) return;
for(int i=0; i < fDeclarations.length; ++i) {
if (fDeclarations[i] == null) break;
if (fDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fDeclarations[i] = (IASTDeclaration) other;
return;
}
}
public void resolveAmbiguities() {
accept(new CASTAmbiguityResolver());
}
/**

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -48,7 +48,10 @@ public class CEnumeration extends PlatformObject implements IEnumeration, ICInte
enumeration.setBinding( this );
}
public void addDeclaration( IASTName decl ){
public void addDeclaration(IASTName decl) {
if (!decl.isActive())
return;
if( decl.getPropertyInParent() != IASTElaboratedTypeSpecifier.TYPE_NAME )
return;
@ -141,10 +144,8 @@ public class CEnumeration extends PlatformObject implements IEnumeration, ICInte
return bindings;
}
/**
* @param name
*/
public void addDefinition( IASTName name ) {
public void addDefinition(IASTName name) {
if (name.isActive())
definition = name;
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -35,6 +35,7 @@ import org.eclipse.cdt.core.dom.ast.gnu.c.ICASTKnRFunctionDeclarator;
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.ASTQueries;
import org.eclipse.core.runtime.PlatformObject;
/**
@ -68,6 +69,9 @@ public class CFunction extends PlatformObject implements IFunction, ICInternalFu
return null;
}
public void addDeclarator( IASTFunctionDeclarator fnDeclarator ){
if (!fnDeclarator.isActive())
return;
if( fnDeclarator.getParent() instanceof IASTFunctionDefinition || fnDeclarator instanceof ICASTKnRFunctionDeclarator ) {
if (definition == fnDeclarator) {
// recursion?
@ -134,7 +138,7 @@ public class CFunction extends PlatformObject implements IFunction, ICInternalFu
if( size > 0 ){
for( int i = 0; i < size; i++ ){
IASTParameterDeclaration p = params[i];
result[i] = (IParameter) CVisitor.findInnermostDeclarator(p.getDeclarator()).getName().resolveBinding();
result[i] = (IParameter) ASTQueries.findInnermostDeclarator(p.getDeclarator()).getName().resolveBinding();
}
}
} else if (dtor instanceof ICASTKnRFunctionDeclarator) {
@ -270,7 +274,7 @@ public class CFunction extends PlatformObject implements IFunction, ICInternalFu
IASTParameterDeclaration [] parameters = ((IASTStandardFunctionDeclarator)definition).getParameters();
if( parameters.length > idx ) {
temp = parameters[idx];
CVisitor.findInnermostDeclarator(temp.getDeclarator()).getName().setBinding( binding );
ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName().setBinding( binding );
}
} else if( definition instanceof ICASTKnRFunctionDeclarator ){
fKnRDtor = (ICASTKnRFunctionDeclarator) definition;
@ -289,7 +293,7 @@ public class CFunction extends PlatformObject implements IFunction, ICInternalFu
for( int j = 0; j < declarators.length && declarators[j] != null; j++ ){
if( declarators[j].getParameters().length > idx ){
temp = declarators[j].getParameters()[idx];
CVisitor.findInnermostDeclarator(temp.getDeclarator()).getName().setBinding( binding );
ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName().setBinding( binding );
}
}
}
@ -305,7 +309,7 @@ public class CFunction extends PlatformObject implements IFunction, ICInternalFu
if(params.length < nps.length )
return;
for( int i = 0; i < nps.length; i++ ){
IASTName name = CVisitor.findInnermostDeclarator(nps[i].getDeclarator()).getName();
IASTName name = ASTQueries.findInnermostDeclarator(nps[i].getDeclarator()).getName();
name.setBinding( params[i] );
if( params[i] instanceof CParameter )
((CParameter)params[i]).addDeclaration( name );

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -142,9 +142,9 @@ public class CParameter extends PlatformObject implements IParameter {
/**
* @param name
*/
public void addDeclaration( IASTName name ) {
if( name != null )
declarations = (IASTName[]) ArrayUtil.append( IASTName.class, declarations, name );
public void addDeclaration(IASTName name) {
if (name != null && name.isActive())
declarations = (IASTName[]) ArrayUtil.append(IASTName.class, declarations, name);
}
/* (non-Javadoc)

View file

@ -222,16 +222,15 @@ public class CStructure extends PlatformObject implements ICompositeType, ICInte
return t;
}
/**
* @param compositeTypeSpec
*/
public void addDefinition(ICASTCompositeTypeSpecifier compositeTypeSpec) {
if (compositeTypeSpec.isActive()) {
definition = compositeTypeSpec.getName();
compositeTypeSpec.getName().setBinding( this );
compositeTypeSpec.getName().setBinding(this);
}
}
public void addDeclaration(IASTName decl) {
if (decl.getPropertyInParent() != IASTElaboratedTypeSpecifier.TYPE_NAME)
if (!decl.isActive() || decl.getPropertyInParent() != IASTElaboratedTypeSpecifier.TYPE_NAME)
return;
decl.setBinding(this);

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -29,6 +29,7 @@ import org.eclipse.cdt.core.dom.ast.IValue;
import org.eclipse.cdt.core.dom.ast.IVariable;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.Linkage;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IInternalVariable;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.Value;
@ -72,9 +73,12 @@ public class CVariable extends PlatformObject implements IInternalVariable, ICIn
return declarations[0];
}
public void addDeclaration( IASTName name ){
declarations = (IASTName[]) ArrayUtil.append( IASTName.class, declarations, name );
public void addDeclaration(IASTName name) {
if (name != null && name.isActive()) {
declarations = (IASTName[]) ArrayUtil.append(IASTName.class, declarations, name);
}
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.IVariable#getType()
*/
@ -198,6 +202,6 @@ public class CVariable extends PlatformObject implements IInternalVariable, ICIn
if (!(node instanceof IASTDeclarator))
return null;
return CVisitor.findOutermostDeclarator((IASTDeclarator) node);
return ASTQueries.findOutermostDeclarator((IASTDeclarator) node);
}
}

View file

@ -480,7 +480,7 @@ public class CVisitor extends ASTQueries {
} catch (DOMException e) {
}
}
if (binding != null && !(binding instanceof IIndexBinding)) {
if (binding != null && !(binding instanceof IIndexBinding) && name.isActive()) {
if (binding instanceof IEnumeration) {
if (binding instanceof CEnumeration) {
((CEnumeration)binding).addDefinition(name);
@ -546,7 +546,7 @@ public class CVisitor extends ASTQueries {
binding= scope.getBinding(name, false);
} catch (DOMException e) {
}
if (binding != null) {
if (binding != null && name.isActive()) {
if (binding instanceof CEnumeration) {
((CEnumeration)binding).addDeclaration(name);
} else if (binding instanceof CStructure) {
@ -559,7 +559,7 @@ public class CVisitor extends ASTQueries {
insertIntoScope= elabTypeSpec.getTranslationUnit().getScope();
try {
binding= insertIntoScope.getBinding(name, false);
if (binding != null) {
if (binding != null && name.isActive()) {
if (binding instanceof CEnumeration) {
((CEnumeration)binding).addDeclaration(name);
} else if (binding instanceof CStructure) {
@ -691,7 +691,7 @@ public class CVisitor extends ASTQueries {
binding = scope.getBinding(name, false);
} catch (DOMException e) {
}
if (binding != null && binding instanceof IIndexBinding == false) {
if (binding != null && !(binding instanceof IIndexBinding) && name.isActive()) {
if (binding instanceof ICInternalFunction)
((ICInternalFunction)binding).addDeclarator((ICASTKnRFunctionDeclarator) declarator);
else
@ -755,7 +755,7 @@ public class CVisitor extends ASTQueries {
return binding;
}
} else if (funcDeclarator != null) {
if (binding != null && !(binding instanceof IIndexBinding)) {
if (binding != null && !(binding instanceof IIndexBinding) && name.isActive()) {
if (binding instanceof IFunction) {
IFunction function = (IFunction) binding;
if (function instanceof CFunction) {
@ -774,7 +774,7 @@ public class CVisitor extends ASTQueries {
binding = new CTypedef(name);
} else {
IType t1 = null, t2 = null;
if (binding != null && !(binding instanceof IIndexBinding)) {
if (binding != null && !(binding instanceof IIndexBinding) && name.isActive()) {
if (binding instanceof IParameter) {
return new ProblemBinding(name, IProblemBinding.SEMANTIC_INVALID_REDECLARATION, name.toCharArray());
} else if (binding instanceof IVariable) {
@ -812,7 +812,7 @@ public class CVisitor extends ASTQueries {
if (scope != null) {
binding = scope.getBinding(name, false);
if (binding != null && !(binding instanceof IIndexBinding)) {
if (binding != null && !(binding instanceof IIndexBinding) && name.isActive()) {
if (binding instanceof CStructure)
((CStructure)binding).addDefinition(compositeTypeSpec);
return binding;

View file

@ -137,7 +137,7 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
}
protected IASTInitializer optionalCInitializer() throws EndOfFileException, BacktrackException {
if (LT(1) == IToken.tASSIGN) {
if (LTcatchEOF(1) == IToken.tASSIGN) {
consume();
return cInitializerClause(false);
}
@ -414,9 +414,10 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
for (IASTDeclarator declarator : declarators)
simpleDeclaration.addDeclarator(declarator);
((ASTNode) simpleDeclaration).setOffsetAndLength(firstOffset, endOffset-firstOffset);
setRange(simpleDeclaration, firstOffset, endOffset);
if ( altDeclSpec != null && altDeclarator != null) {
simpleDeclaration= new CASTAmbiguousSimpleDeclaration(simpleDeclaration, altDeclSpec, altDeclarator);
setRange(simpleDeclaration, firstOffset, endOffset);
}
if (insertSemi) {
@ -1221,48 +1222,7 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
name= nodeFactory.newName();
}
ICASTCompositeTypeSpecifier result = nodeFactory.newCompositeTypeSpecifier(classKind, name);
int endOffset= consume().getEndOffset();
int declOffset= -1;
loop: while (true) {
try {
IToken next= LAcatchEOF(1);
if (next == null || next.getType() == IToken.tEOC)
break loop; // the missing semicolon will cause a problem, just break the loop.
if (next.getType() == IToken.tRBRACE) {
endOffset= consume().getEndOffset();
break loop;
}
final int nextOffset = next.getOffset();
declarationMark= next;
next= null; // don't hold on to the token while parsing namespaces, class bodies, etc.
IASTDeclaration d;
if (declOffset == nextOffset) {
// no progress
d= skipProblemDeclaration(declOffset);
} else {
d = declaration(DeclarationOptions.C_MEMBER);
}
result.addMemberDeclaration(d);
endOffset= calculateEndOffset(d);
} catch (BacktrackException bt) {
IASTDeclaration[] decls= problemDeclaration(declOffset, bt, DeclarationOptions.C_MEMBER);
for (IASTDeclaration declaration : decls) {
result.addMemberDeclaration(declaration);
endOffset= calculateEndOffset(declaration);
}
} catch (EndOfFileException e) {
result.addMemberDeclaration(skipProblemDeclaration(declOffset));
endOffset= eofOffset;
break loop;
} finally {
declarationMark= null;
}
}
((ASTNode) result).setOffsetAndLength(offset, endOffset - offset);
declarationListInBraces(result, offset, DeclarationOptions.C_MEMBER);
return result;
}
@ -1302,7 +1262,7 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
throws EndOfFileException, BacktrackException, FoundAggregateInitializer {
IASTDeclarator d = declarator(option);
if (LT(1) == IToken.tASSIGN && LT(2) == IToken.tLBRACE)
if (LTcatchEOF(1) == IToken.tASSIGN && LT(2) == IToken.tLBRACE)
throw new FoundAggregateInitializer(d);
IASTInitializer i = optionalCInitializer();
@ -1409,8 +1369,9 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
final int startingOffset, int endOffset,
final DeclarationOptions option) throws EndOfFileException, BacktrackException {
IASTDeclarator result= null;
int lt1;
loop: while(true) {
final int lt1= LT(1);
lt1= LTcatchEOF(1);
switch (lt1) {
case IToken.tLPAREN:
result= functionDeclarator(isAbstract(declaratorName, nestedDeclarator)
@ -1445,6 +1406,7 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
break loop;
}
}
if (lt1 != 0)
__attribute_decl_seq(supportAttributeSpecifiers, supportDeclspecSpecifiers);
if (result == null) {
@ -1454,7 +1416,7 @@ public class GNUCSourceParser extends AbstractGNUSourceCodeParser {
endOffset= calculateEndOffset(result);
}
if (LT(1) == IToken.t_asm) { // asm labels bug 226121
if (lt1 != 0 && LT(1) == IToken.t_asm) { // asm labels bug 226121
consume();
endOffset= asmExpression(null).getEndOffset();

View file

@ -54,6 +54,7 @@ final class CPPASTAmbiguityResolver extends ASTVisitor {
public CPPASTAmbiguityResolver() {
super(false);
includeInactiveNodes= true;
shouldVisitAmbiguousNodes= true;
shouldVisitDeclarations= true;
shouldVisitDeclSpecifiers= true;

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -19,6 +19,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCompositeTypeSpecifier;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTVisibilityLabel;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPClassScope;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/**
@ -27,21 +28,26 @@ import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
public class CPPASTCompositeTypeSpecifier extends CPPASTBaseDeclSpecifier
implements ICPPASTCompositeTypeSpecifier, IASTAmbiguityParent {
private int k;
private IASTName n;
private ICPPClassScope scope;
private int fKey;
private IASTName fName;
private ICPPClassScope fScope;
private IASTDeclaration[] fAllDeclarations;
private IASTDeclaration[] fActiveDeclarations;
private int fDeclarationsPos=-1;
private ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier[] baseSpecs = null;
private int baseSpecsPos = -1;
public CPPASTCompositeTypeSpecifier() {
}
public CPPASTCompositeTypeSpecifier(int k, IASTName n) {
this.k = k;
this.fKey = k;
setName(n);
}
public CPPASTCompositeTypeSpecifier copy() {
CPPASTCompositeTypeSpecifier copy = new CPPASTCompositeTypeSpecifier(k, n == null ? null : n.copy());
CPPASTCompositeTypeSpecifier copy = new CPPASTCompositeTypeSpecifier(fKey, fName == null ? null : fName.copy());
copyBaseDeclSpec(copy);
for(IASTDeclaration member : getMembers())
copy.addMemberDeclaration(member == null ? null : member.copy());
@ -66,21 +72,21 @@ public class CPPASTCompositeTypeSpecifier extends CPPASTBaseDeclSpecifier
}
public int getKey() {
return k;
return fKey;
}
public void setKey(int key) {
assertNotFrozen();
k = key;
fKey = key;
}
public IASTName getName() {
return n;
return fName;
}
public void setName(IASTName name) {
assertNotFrozen();
this.n = name;
this.fName = name;
if (name != null) {
name.setParent(this);
name.setPropertyInParent(TYPE_NAME);
@ -88,82 +94,95 @@ public class CPPASTCompositeTypeSpecifier extends CPPASTBaseDeclSpecifier
}
public IASTDeclaration[] getMembers() {
if( declarations == null ) return IASTDeclaration.EMPTY_DECLARATION_ARRAY;
return (IASTDeclaration[]) ArrayUtil.trim( IASTDeclaration.class, declarations );
IASTDeclaration[] active= fActiveDeclarations;
if (active == null) {
active = ASTQueries.extractActiveDeclarations(fAllDeclarations, fDeclarationsPos+1);
fActiveDeclarations= active;
}
return active;
}
public final IASTDeclaration[] getDeclarations(boolean includeInactive) {
if (includeInactive) {
fAllDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, fAllDeclarations, fDeclarationsPos);
return fAllDeclarations;
}
return getMembers();
}
public void addMemberDeclaration(IASTDeclaration decl) {
if (decl == null)
return;
// ignore inactive visibility labels
if (decl instanceof ICPPASTVisibilityLabel && !decl.isActive())
return;
assertNotFrozen();
declarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, declarations, decl );
if(decl != null) {
decl.setParent(this);
decl.setPropertyInParent(decl instanceof ICPPASTVisibilityLabel ? VISIBILITY_LABEL : MEMBER_DECLARATION);
}
fAllDeclarations = (IASTDeclaration[]) ArrayUtil.append(IASTDeclaration.class, fAllDeclarations,
++fDeclarationsPos, decl);
fActiveDeclarations= null;
}
private IASTDeclaration [] declarations = new IASTDeclaration[4];
private ICPPASTCompositeTypeSpecifier.ICPPASTBaseSpecifier [] baseSpecs = null;
private int baseSpecsPos=-1;
public final void addDeclaration(IASTDeclaration decl) {
addMemberDeclaration(decl);
}
public ICPPClassScope getScope() {
if( scope == null )
scope = new CPPClassScope( this );
return scope;
if (fScope == null)
fScope = new CPPClassScope(this);
return fScope;
}
public void setScope(ICPPClassScope scope) {
this.scope = scope;
this.fScope = scope;
}
@Override
public boolean accept( ASTVisitor action ){
if( action.shouldVisitDeclSpecifiers ){
switch( action.visit( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
public boolean accept(ASTVisitor action) {
if (action.shouldVisitDeclSpecifiers) {
switch (action.visit(this)) {
case ASTVisitor.PROCESS_ABORT: return false;
case ASTVisitor.PROCESS_SKIP: return true;
default: break;
}
}
if( n != null ) if( !n.accept( action ) ) return false;
if (fName != null && !fName.accept(action))
return false;
ICPPASTBaseSpecifier[] bases = getBaseSpecifiers();
for( int i = 0; i < bases.length; i++ )
if( !bases[i].accept( action ) ) return false;
IASTDeclaration [] decls = getMembers();
for( int i = 0; i < decls.length; i++ )
if( !decls[i].accept( action ) ) return false;
if( action.shouldVisitDeclSpecifiers ){
switch( action.leave( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
for (int i = 0; i < bases.length; i++) {
if (!bases[i].accept(action)) return false;
}
IASTDeclaration[] decls = getDeclarations(action.includeInactiveNodes);
for (int i = 0; i < decls.length; i++) {
if (!decls[i].accept(action)) return false;
}
if (action.shouldVisitDeclSpecifiers && action.leave(this) == ASTVisitor.PROCESS_ABORT)
return false;
return true;
}
public int getRoleForName(IASTName name) {
if( name == this.n )
if( name == this.fName )
return r_definition;
return r_unclear;
}
public void replace(IASTNode child, IASTNode other) {
if( declarations == null ) return;
for( int i = 0; i < declarations.length; ++i )
{
if( declarations[i] == null ) {
break;
}
if( declarations[i] == child )
{
other.setParent( child.getParent() );
other.setPropertyInParent( child.getPropertyInParent() );
declarations[i] = (IASTDeclaration) other;
assert child.isActive() == other.isActive();
for (int i = 0; i <= fDeclarationsPos; ++i) {
if (fAllDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fAllDeclarations[i] = (IASTDeclaration) other;
fActiveDeclarations= null;
}
}
}

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
* 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:
* IBM - Initial API and implementation
* John Camelon (IBM) - Initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -16,25 +16,29 @@ import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTLinkageSpecification;
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.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/**
* @author jcamelon
* Extern "C" construct.
*/
public class CPPASTLinkageSpecification extends ASTNode implements
ICPPASTLinkageSpecification, IASTAmbiguityParent {
private String literal;
private String fLiteral;
private IASTDeclaration[] fAllDeclarations;
private IASTDeclaration[] fActiveDeclarations;
private int fLastDeclaration=-1;
public CPPASTLinkageSpecification() {
}
public CPPASTLinkageSpecification(String literal) {
this.literal = literal;
this.fLiteral = literal;
}
public CPPASTLinkageSpecification copy() {
CPPASTLinkageSpecification copy = new CPPASTLinkageSpecification(literal);
CPPASTLinkageSpecification copy = new CPPASTLinkageSpecification(fLiteral);
for(IASTDeclaration declaration : getDeclarations())
copy.addDeclaration(declaration == null ? null : declaration.copy());
copy.setOffsetAndLength(this);
@ -43,65 +47,71 @@ public class CPPASTLinkageSpecification extends ASTNode implements
public String getLiteral() {
return literal;
return fLiteral;
}
public void setLiteral(String value) {
assertNotFrozen();
this.literal = value;
this.fLiteral = value;
}
public IASTDeclaration [] getDeclarations() {
if( declarations == null ) return IASTDeclaration.EMPTY_DECLARATION_ARRAY;
return (IASTDeclaration[]) ArrayUtil.trim( IASTDeclaration.class, declarations );
}
public void addDeclaration(IASTDeclaration declaration) {
assertNotFrozen();
declarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, declarations, declaration );
if(declaration != null) {
declaration.setParent(this);
declaration.setPropertyInParent(OWNED_DECLARATION);
public final void addDeclaration(IASTDeclaration decl) {
if (decl != null) {
decl.setParent(this);
decl.setPropertyInParent(OWNED_DECLARATION);
fAllDeclarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, fAllDeclarations, ++fLastDeclaration, decl);
fActiveDeclarations= null;
}
}
private IASTDeclaration [] declarations = new IASTDeclaration[4];
public final IASTDeclaration[] getDeclarations() {
IASTDeclaration[] active= fActiveDeclarations;
if (active == null) {
active = ASTQueries.extractActiveDeclarations(fAllDeclarations, fLastDeclaration+1);
fActiveDeclarations= active;
}
return active;
}
public final IASTDeclaration[] getDeclarations(boolean includeInactive) {
if (includeInactive) {
fAllDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, fAllDeclarations, fLastDeclaration);
return fAllDeclarations;
}
return getDeclarations();
}
@Override
public boolean accept( ASTVisitor action ){
if( action.shouldVisitDeclarations ){
switch( action.visit( this ) ){
public boolean accept(ASTVisitor action) {
if (action.shouldVisitDeclarations) {
switch (action.visit(this)) {
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
}
IASTDeclaration [] decls = getDeclarations();
for( int i = 0; i < decls.length; i++ )
if( !decls[i].accept( action ) ) return false;
IASTDeclaration[] decls = getDeclarations(action.includeInactiveNodes);
for (IASTDeclaration decl : decls) {
if (!decl.accept(action)) return false;
}
if( action.shouldVisitDeclarations ){
switch( action.leave( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
}
if (action.shouldVisitDeclarations && action.leave(this) == ASTVisitor.PROCESS_ABORT)
return false;
return true;
}
public void replace(IASTNode child, IASTNode other) {
if( declarations == null ) return;
for( int i = 0; i < declarations.length; ++i )
{
if( declarations[i] == null ) continue;
if( declarations[i] == child )
{
other.setParent( child.getParent() );
other.setPropertyInParent( child.getPropertyInParent() );
declarations[i] = (IASTDeclaration) other;
public final void replace(IASTNode child, IASTNode other) {
assert child.isActive() == other.isActive();
for (int i = 0; i <= fLastDeclaration; ++i) {
if (fAllDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fAllDeclarations[i] = (IASTDeclaration) other;
fActiveDeclarations= null;
return;
}
}
}

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
* 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:
* 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;
@ -22,15 +22,19 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTVisitor;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespace;
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.ASTQueries;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
/**
* @author jcamelon
* Definition of a namespace.
*/
public class CPPASTNamespaceDefinition extends ASTNode implements
ICPPASTNamespaceDefinition, IASTAmbiguityParent {
private IASTName name;
private IASTName fName;
private IASTDeclaration[] fAllDeclarations;
private IASTDeclaration[] fActiveDeclarations;
private int fLastDeclaration=-1;
public CPPASTNamespaceDefinition() {
}
@ -40,7 +44,7 @@ public class CPPASTNamespaceDefinition extends ASTNode implements
}
public CPPASTNamespaceDefinition copy() {
CPPASTNamespaceDefinition copy = new CPPASTNamespaceDefinition(name == null ? null : name.copy());
CPPASTNamespaceDefinition copy = new CPPASTNamespaceDefinition(fName == null ? null : fName.copy());
for(IASTDeclaration declaration : getDeclarations())
copy.addDeclaration(declaration == null ? null : declaration.copy());
copy.setOffsetAndLength(this);
@ -48,83 +52,91 @@ public class CPPASTNamespaceDefinition extends ASTNode implements
}
public IASTName getName() {
return name;
return fName;
}
public void setName(IASTName name) {
assertNotFrozen();
this.name = name;
this.fName = name;
if (name != null) {
name.setParent(this);
name.setPropertyInParent(NAMESPACE_NAME);
}
}
public IASTDeclaration [] getDeclarations() {
if( declarations == null ) return IASTDeclaration.EMPTY_DECLARATION_ARRAY;
return (IASTDeclaration[]) ArrayUtil.trim( IASTDeclaration.class, declarations );
}
public void addDeclaration(IASTDeclaration declaration) {
assertNotFrozen();
declarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, declarations, declaration );
if(declaration != null) {
declaration.setParent(this);
declaration.setPropertyInParent(OWNED_DECLARATION);
public final void addDeclaration(IASTDeclaration decl) {
if (decl != null) {
decl.setParent(this);
decl.setPropertyInParent(OWNED_DECLARATION);
fAllDeclarations = (IASTDeclaration[]) ArrayUtil.append( IASTDeclaration.class, fAllDeclarations, ++fLastDeclaration, decl);
fActiveDeclarations= null;
}
}
private IASTDeclaration [] declarations = new IASTDeclaration[32];
public final IASTDeclaration[] getDeclarations() {
IASTDeclaration[] active= fActiveDeclarations;
if (active == null) {
active = ASTQueries.extractActiveDeclarations(fAllDeclarations, fLastDeclaration+1);
fActiveDeclarations= active;
}
return active;
}
public final IASTDeclaration[] getDeclarations(boolean includeInactive) {
if (includeInactive) {
fAllDeclarations= (IASTDeclaration[]) ArrayUtil.removeNullsAfter(IASTDeclaration.class, fAllDeclarations, fLastDeclaration);
return fAllDeclarations;
}
return getDeclarations();
}
public IScope getScope() {
try {
return ((ICPPNamespace) name.resolveBinding()).getNamespaceScope();
return ((ICPPNamespace) fName.resolveBinding()).getNamespaceScope();
} catch ( DOMException e ) {
return e.getProblem();
}
}
@Override
public boolean accept( ASTVisitor action ){
public boolean accept(ASTVisitor action) {
if (action.shouldVisitNamespaces && action instanceof ICPPASTVisitor) {
switch( ((ICPPASTVisitor)action).visit( this ) ){
switch (((ICPPASTVisitor) action).visit(this)) {
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
}
if( name != null ) if( !name.accept( action ) ) return false;
IASTDeclaration [] decls = getDeclarations();
for ( int i = 0; i < decls.length; i++ )
if( !decls[i].accept( action ) ) return false;
if (fName != null && !fName.accept(action))
return false;
if (action.shouldVisitNamespaces && action instanceof ICPPASTVisitor) {
switch( ((ICPPASTVisitor)action).leave( this ) ){
case ASTVisitor.PROCESS_ABORT : return false;
case ASTVisitor.PROCESS_SKIP : return true;
default : break;
}
IASTDeclaration [] decls = getDeclarations(action.includeInactiveNodes);
for (IASTDeclaration decl : decls) {
if (!decl.accept(action)) return false;
}
if (action.shouldVisitNamespaces && action instanceof ICPPASTVisitor &&
((ICPPASTVisitor) action).leave(this) == ASTVisitor.PROCESS_ABORT)
return false;
return true;
}
public int getRoleForName(IASTName n) {
if( name == n ) return r_definition;
if( fName == n ) return r_definition;
return r_unclear;
}
public void replace(IASTNode child, IASTNode other) {
if( declarations == null ) return;
for( int i = 0; i < declarations.length; ++i )
{
if( declarations[i] == null ) break;
if( declarations[i] == child )
{
other.setParent( child.getParent() );
other.setPropertyInParent( child.getPropertyInParent() );
declarations[i] = (IASTDeclaration) other;
assert child.isActive() == other.isActive();
for (int i = 0; i <= fLastDeclaration; ++i) {
if (fAllDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fAllDeclarations[i] = (IASTDeclaration) other;
fActiveDeclarations= null;
return;
}
}
}

View file

@ -12,11 +12,7 @@
package org.eclipse.cdt.internal.core.dom.parser.cpp;
import org.eclipse.cdt.core.dom.ILinkage;
import org.eclipse.cdt.core.dom.ast.ASTVisitor;
import org.eclipse.cdt.core.dom.ast.DOMException;
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
import org.eclipse.cdt.core.dom.ast.IASTName;
import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.IBasicType;
import org.eclipse.cdt.core.dom.ast.IBinding;
import org.eclipse.cdt.core.dom.ast.IMacroBinding;
@ -32,7 +28,6 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPNamespaceScope;
import org.eclipse.cdt.core.parser.ParserLanguage;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
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.ASTTranslationUnit;
import org.eclipse.cdt.internal.core.dom.parser.IASTAmbiguityParent;
import org.eclipse.cdt.internal.core.dom.parser.GCCBuiltinSymbolProvider.CPPBuiltinParameter;
@ -57,10 +52,6 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
return copy;
}
@Override
public void cleanupAfterAmbiguityResolution() {
}
public CPPNamespaceScope getScope() {
if (fScope == null) {
fScope = new CPPNamespaceScope(this);
@ -69,7 +60,7 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
return fScope;
}
private void addBuiltinOperators(IScope theScope) {
private void addBuiltinOperators(CPPScope theScope) {
// void
IType cpp_void = new CPPBasicType(IBasicType.t_void, 0);
// void *
@ -85,16 +76,12 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
IParameter[] newTheParms = new IParameter[1];
newTheParms[0] = new CPPBuiltinParameter(newParms[0]);
temp = new CPPImplicitFunction(OverloadableOperator.NEW.toCharArray(), theScope, newFunctionType, newTheParms, false);
try {
ASTInternal.addBinding(theScope, temp);
} catch (DOMException de) {}
theScope.addBinding(temp);
// void * operator new[] (std::size_t);
temp = null;
temp = new CPPImplicitFunction(OverloadableOperator.NEW_ARRAY.toCharArray(), theScope, newFunctionType, newTheParms, false);
try {
ASTInternal.addBinding(theScope, temp);
} catch (DOMException de) {}
theScope.addBinding(temp);
// void operator delete(void*);
temp = null;
@ -104,16 +91,12 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
IParameter[] deleteTheParms = new IParameter[1];
deleteTheParms[0] = new CPPBuiltinParameter(deleteParms[0]);
temp = new CPPImplicitFunction(OverloadableOperator.DELETE.toCharArray(), theScope, deleteFunctionType, deleteTheParms, false);
try {
ASTInternal.addBinding(theScope, temp);
} catch (DOMException de) {}
theScope.addBinding(temp);
// void operator delete[](void*);
temp = null;
temp = new CPPImplicitFunction(OverloadableOperator.DELETE_ARRAY.toCharArray(), theScope, deleteFunctionType, deleteTheParms, false);
try {
ASTInternal.addBinding(theScope, temp);
} catch (DOMException de) {}
theScope.addBinding(temp);
}
public IASTName[] getDeclarationsInAST(IBinding binding) {
@ -149,18 +132,6 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
return fBinding;
}
public void replace(IASTNode child, IASTNode other) {
if (fDeclarations == null) return;
for(int i=0; i < fDeclarations.length; ++i) {
if (fDeclarations[i] == null) break;
if (fDeclarations[i] == child) {
other.setParent(child.getParent());
other.setPropertyInParent(child.getPropertyInParent());
fDeclarations[i] = (IASTDeclaration) other;
}
}
}
public ParserLanguage getParserLanguage() {
return ParserLanguage.CPP;
}
@ -198,7 +169,7 @@ public class CPPASTTranslationUnit extends ASTTranslationUnit implements ICPPAST
}
@Override
protected ASTVisitor createAmbiguityNodeVisitor() {
return new CPPASTAmbiguityResolver();
public void resolveAmbiguities() {
accept(new CPPASTAmbiguityResolver());
}
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2008 Wind River Systems Inc. and others.
* Copyright (c) 2008, 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
@ -87,15 +87,6 @@ public class CPPBuiltinVariable extends CPPVariable {
// do nothing
}
/**
* does nothing
*/
@Override
public void removeDeclaration(IASTNode node) {
// do nothing
}
@Override
public String[] getQualifiedName() {
String[] temp = new String[1];

View file

@ -163,6 +163,10 @@ public class CPPClassScope extends CPPScope implements ICPPClassScope {
@Override
public void addName(IASTName name) throws DOMException {
// don't add names from inactive code branches
if (!name.isActive())
return;
if (name instanceof ICPPASTQualifiedName) {
// check whether the qualification matches
IBinding b= getClassType();

View file

@ -333,14 +333,6 @@ public class CPPClassType extends PlatformObject implements ICPPInternalClassTyp
}
}
public void removeDeclaration(IASTNode node) {
if (definition == node) {
definition = null;
return;
}
ArrayUtil.remove(declarations, node);
}
public String[] getQualifiedName() {
return CPPVisitor.getQualifiedName(this);
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -109,9 +109,6 @@ public class CPPEnumeration extends PlatformObject implements IEnumeration, ICPP
public void addDeclaration(IASTNode node) {
}
public void removeDeclaration(IASTNode node) {
}
public boolean isSameType( IType type ) {
if( type == this )
return true;

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -58,9 +58,6 @@ public class CPPEnumerator extends PlatformObject implements IEnumerator, ICPPIn
return enumName;
}
public void removeDeclaration(IASTNode node) {
}
/* (non-Javadoc)
* @see org.eclipse.cdt.core.dom.ast.IBinding#getName()
*/

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -42,6 +42,7 @@ import org.eclipse.cdt.core.parser.util.ArrayUtil;
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.ASTNode;
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.cpp.semantics.CPPVisitor;
import org.eclipse.core.runtime.PlatformObject;
@ -115,7 +116,7 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
public CPPFunction(ICPPASTFunctionDeclarator declarator) {
if (declarator != null) {
IASTNode parent = CPPVisitor.findOutermostDeclarator(declarator).getParent();
IASTNode parent = ASTQueries.findOutermostDeclarator(declarator).getParent();
if (parent instanceof IASTFunctionDefinition)
definition = declarator;
else
@ -199,25 +200,13 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
node = node.getParent();
if (node instanceof IASTDeclarator == false)
return null;
node= CPPVisitor.findTypeRelevantDeclarator((IASTDeclarator) node);
node= ASTQueries.findTypeRelevantDeclarator((IASTDeclarator) node);
if (node instanceof ICPPASTFunctionDeclarator == false)
return null;
return (ICPPASTFunctionDeclarator) node;
}
public void removeDeclaration(IASTNode node) {
ICPPASTFunctionDeclarator dtor = extractFunctionDtor(node);
if (definition == dtor) {
definition = null;
return;
}
if (declarations != null) {
ArrayUtil.remove(declarations, dtor);
}
}
public IParameter[] getParameters() {
IASTStandardFunctionDeclarator dtor = getPreferredDtor();
IASTParameterDeclaration[] params = dtor.getParameters();
@ -226,7 +215,7 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
if (size > 0) {
for (int i = 0; i < size; i++) {
IASTParameterDeclaration p = params[i];
final IASTName name = CPPVisitor.findInnermostDeclarator(p.getDeclarator()).getName();
final IASTName name = ASTQueries.findInnermostDeclarator(p.getDeclarator()).getName();
final IBinding binding= name.resolveBinding();
if (binding instanceof IParameter) {
result[i]= (IParameter) binding;
@ -262,7 +251,7 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
protected IASTName getASTName() {
IASTDeclarator dtor = (definition != null) ? definition : declarations[0];
dtor= CPPVisitor.findInnermostDeclarator(dtor);
dtor= ASTQueries.findInnermostDeclarator(dtor);
IASTName name= dtor.getName();
if (name instanceof ICPPASTQualifiedName) {
IASTName[] ns = ((ICPPASTQualifiedName)name).getNames();
@ -277,11 +266,11 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
if (scope instanceof ICPPClassScope) {
ICPPASTDeclSpecifier declSpec = null;
if (definition != null) {
IASTNode node = CPPVisitor.findOutermostDeclarator(definition).getParent();
IASTNode node = ASTQueries.findOutermostDeclarator(definition).getParent();
IASTFunctionDefinition def = (IASTFunctionDefinition) node;
declSpec = (ICPPASTDeclSpecifier) def.getDeclSpecifier();
} else {
IASTNode node = CPPVisitor.findOutermostDeclarator(declarations[0]).getParent();
IASTNode node = ASTQueries.findOutermostDeclarator(declarations[0]).getParent();
IASTSimpleDeclaration decl = (IASTSimpleDeclaration)node;
declSpec = (ICPPASTDeclSpecifier) decl.getDeclSpecifier();
}
@ -328,10 +317,10 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
IASTParameterDeclaration[] paramDecls = definition.getParameters();
if (paramDecls.length > i) { // This will be less than i if we have a void parameter
temp = paramDecls[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
if (n != name) {
n.setBinding(binding);
((CPPParameter)binding).addDeclaration(n);
ASTInternal.addDeclaration(binding, n);
}
}
}
@ -340,10 +329,10 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
IASTParameterDeclaration[] paramDecls = declarations[j].getParameters();
if (paramDecls.length > i) {
temp = paramDecls[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
if (n != name) {
n.setBinding(binding);
((CPPParameter)binding).addDeclaration(n);
ASTInternal.addDeclaration(binding, n);
}
}
}
@ -357,14 +346,14 @@ public class CPPFunction extends PlatformObject implements ICPPFunction, ICPPInt
IASTParameterDeclaration[] nps = fdtor.getParameters();
CPPParameter temp = null;
for (int i = 0; i < ops.length; i++) {
temp = (CPPParameter) CPPVisitor.findInnermostDeclarator(ops[i].getDeclarator()).getName().getBinding();
temp = (CPPParameter) ASTQueries.findInnermostDeclarator(ops[i].getDeclarator()).getName().getBinding();
if (temp != null && nps.length > i) { //length could be different, ie 0 or 1 with void
IASTDeclarator dtor = nps[i].getDeclarator();
while (dtor.getNestedDeclarator() != null)
dtor = dtor.getNestedDeclarator();
IASTName name = dtor.getName();
name.setBinding(temp);
temp.addDeclaration(name);
ASTInternal.addDeclaration(temp, name);
}
}
}

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -31,6 +31,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPParameter;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameterMap;
import org.eclipse.cdt.core.index.IIndexBinding;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
/**
@ -179,10 +180,10 @@ public class CPPFunctionSpecialization extends CPPSpecialization implements ICPP
try {
IParameter[] params = getParameters();
if (i < params.length) {
name.setBinding(params[i]);
if (params[i] instanceof ICPPInternalBinding)
((ICPPInternalBinding)params[i]).addDeclaration(name);
return params[i];
final IParameter myParam = params[i];
name.setBinding(myParam);
ASTInternal.addDeclaration(myParam, name);
return myParam;
}
} catch (DOMException e) {
@ -222,15 +223,14 @@ public class CPPFunctionSpecialization extends CPPSpecialization implements ICPP
}
IASTParameterDeclaration[] nps = fdtor.getParameters();
for (int i = 0; i < nps.length; i++) {
//temp = (CPPParameter) ops[i].getDeclarator().getName().getBinding();
if (params[i] != null) {
final IParameter param = params[i];
if (param != null) {
IASTDeclarator dtor = nps[i].getDeclarator();
while (dtor.getNestedDeclarator() != null)
dtor = dtor.getNestedDeclarator();
IASTName name = dtor.getName();
name.setBinding(params[i]);
if (params[i] instanceof ICPPInternalBinding)
((ICPPInternalBinding) params[i]).addDeclaration(name);
name.setBinding(param);
ASTInternal.addDeclaration(param, name);
}
}
}

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -35,6 +35,8 @@ 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.ICPPFunctionType;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
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.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
@ -130,11 +132,11 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
IASTParameterDeclaration[] nps = getDeclaratorByName(declName).getParameters();
CPPParameter temp = null;
for(int i = 0; i < nps.length; i++) {
temp = (CPPParameter) CPPVisitor.findInnermostDeclarator(ops[i].getDeclarator()).getName().getBinding();
temp = (CPPParameter) ASTQueries.findInnermostDeclarator(ops[i].getDeclarator()).getName().getBinding();
if (temp != null) {
IASTName name = CPPVisitor.findInnermostDeclarator(nps[i].getDeclarator()).getName();
IASTName name = ASTQueries.findInnermostDeclarator(nps[i].getDeclarator()).getName();
name.setBinding(temp);
temp.addDeclaration(name);
ASTInternal.addDeclaration(temp, name);
}
}
}
@ -149,7 +151,7 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
if (size > 0) {
for(int i = 0; i < size; i++) {
IASTParameterDeclaration p = params[i];
final IASTName pname = CPPVisitor.findInnermostDeclarator(p.getDeclarator()).getName();
final IASTName pname = ASTQueries.findInnermostDeclarator(p.getDeclarator()).getName();
final IBinding binding= pname.resolveBinding();
if (binding instanceof IParameter) {
result[i]= (IParameter) binding;
@ -211,7 +213,7 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
}
public IBinding resolveParameter(IASTParameterDeclaration param) {
IASTName name = CPPVisitor.findInnermostDeclarator(param.getDeclarator()).getName();
IASTName name = ASTQueries.findInnermostDeclarator(param.getDeclarator()).getName();
IBinding binding = name.getBinding();
if (binding != null)
return binding;
@ -231,10 +233,10 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
ICPPASTFunctionDeclarator fdecl= getDeclaratorByName(definition);
if (fdecl != null) {
temp = fdecl.getParameters()[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
if (n != name) {
n.setBinding(binding);
((CPPParameter)binding).addDeclaration(n);
ASTInternal.addDeclaration(binding, n);
}
}
}
@ -243,10 +245,10 @@ public class CPPFunctionTemplate extends CPPTemplateDefinition
ICPPASTFunctionDeclarator fdecl= getDeclaratorByName(declarations[j]);
if (fdecl != null) {
temp = fdecl.getParameters()[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
if (n != name) {
n.setBinding(binding);
((CPPParameter)binding).addDeclaration(n);
ASTInternal.addDeclaration(binding, n);
}
}
}

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -18,7 +18,8 @@ import org.eclipse.cdt.core.dom.ast.IParameter;
import org.eclipse.cdt.core.dom.ast.IScope;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTFunctionDeclarator;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPFunctionType;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPVisitor;
import org.eclipse.cdt.internal.core.dom.parser.ASTInternal;
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
/**
* The CPPImplicitFunction is used to represent implicit functions that exist on the translation
@ -82,53 +83,53 @@ public class CPPImplicitFunction extends CPPFunction {
}
@Override
public IBinding resolveParameter( IASTParameterDeclaration param ){
IASTName aName = CPPVisitor.findInnermostDeclarator(param.getDeclarator()).getName();
public IBinding resolveParameter(IASTParameterDeclaration param) {
IASTName aName = ASTQueries.findInnermostDeclarator(param.getDeclarator()).getName();
IParameter binding = (IParameter) aName.getBinding();
if( binding != null )
if (binding != null)
return binding;
//get the index in the parameter list
// get the index in the parameter list
ICPPASTFunctionDeclarator fdtor = (ICPPASTFunctionDeclarator) param.getParent();
IASTParameterDeclaration [] ps = fdtor.getParameters();
IASTParameterDeclaration[] ps = fdtor.getParameters();
int i = 0;
for( ; i < ps.length; i++ ){
if( param == ps[i] )
for (; i < ps.length; i++) {
if (param == ps[i])
break;
}
//set the binding for the corresponding parameter in all known defns and decls
// set the binding for the corresponding parameter in all known defns and decls
binding = parms[i];
IASTParameterDeclaration temp = null;
if( definition != null ){
if (definition != null) {
temp = definition.getParameters()[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
n.setBinding( binding );
((CPPParameter)binding).addDeclaration( n );
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
n.setBinding(binding);
ASTInternal.addDeclaration(binding, n);
}
if( declarations != null ){
for( int j = 0; j < declarations.length && declarations[j] != null; j++ ){
if (declarations != null) {
for (int j = 0; j < declarations.length && declarations[j] != null; j++) {
temp = declarations[j].getParameters()[i];
IASTName n = CPPVisitor.findInnermostDeclarator(temp.getDeclarator()).getName();
n.setBinding( binding );
((CPPParameter)binding).addDeclaration( n );
IASTName n = ASTQueries.findInnermostDeclarator(temp.getDeclarator()).getName();
n.setBinding(binding);
ASTInternal.addDeclaration(binding, n);
}
}
return binding;
}
@Override
protected void updateParameterBindings( ICPPASTFunctionDeclarator fdtor ){
if( parms != null ){
IASTParameterDeclaration [] nps = fdtor.getParameters();
if( nps.length != parms.length )
protected void updateParameterBindings(ICPPASTFunctionDeclarator fdtor) {
if (parms != null) {
IASTParameterDeclaration[] nps = fdtor.getParameters();
if (nps.length != parms.length)
return;
for( int i = 0; i < nps.length; i++ ){
IASTName aName = CPPVisitor.findInnermostDeclarator(nps[i].getDeclarator()).getName();
aName.setBinding( parms[i] );
if( parms[i] instanceof ICPPInternalBinding )
((ICPPInternalBinding)parms[i]).addDeclaration( aName );
for (int i = 0; i < nps.length; i++) {
IASTName aName = ASTQueries.findInnermostDeclarator(nps[i].getDeclarator()).getName();
final IParameter param = parms[i];
aName.setBinding(param);
ASTInternal.addDeclaration(param, aName);
}
}
}

View file

@ -149,9 +149,9 @@ public class CPPImplicitMethod extends CPPImplicitFunction implements ICPPMethod
if (ok) {
name.setBinding(this);
if (member instanceof IASTSimpleDeclaration)
addDeclaration(dtor);
ASTInternal.addDeclaration(this, dtor);
else if (member instanceof IASTFunctionDefinition)
addDefinition(dtor);
ASTInternal.addDefinition(this, dtor);
return member;
}
}

View file

@ -1,12 +1,13 @@
/*******************************************************************************
* 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
* 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:
* IBM - Initial API and implementation
* Devin Steffler (IBM) - Initial API and implementation
* Markus Schorn (Wind River Systems)
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -21,8 +22,6 @@ import org.eclipse.cdt.core.dom.ast.ITypedef;
* unit but are not actually part of the physical AST created by CDT.
*
* An example is the GCC built-in typedef: typedef char * __builtin_va_list;
*
* @author dsteffle
*/
public class CPPImplicitTypedef extends CPPTypedef {
private IType type=null;
@ -115,15 +114,6 @@ public class CPPImplicitTypedef extends CPPTypedef {
// do nothing
}
/**
* does nothing
*/
@Override
public void removeDeclaration(IASTNode node) {
// do nothing
}
@Override
public String[] getQualifiedName() {
String[] temp = new String[1];

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -88,8 +88,6 @@ public class CPPLabel extends PlatformObject implements ILabel, ICPPInternalBind
public void addDeclaration(IASTNode node) {
}
public void removeDeclaration(IASTNode node) {
}
public ILinkage getLinkage() {
return Linkage.CPP_LINKAGE;

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -303,8 +303,8 @@ public class CPPNamespace extends PlatformObject implements ICPPNamespace, ICPPI
public void addDefinition(IASTNode node) {
if (!(node instanceof IASTName))
return;
IASTName name = (IASTName) node;
IASTName name = (IASTName) node;
if (namespaceDefinitions == null) {
namespaceDefinitions = new IASTName[] { name };
return;
@ -323,9 +323,6 @@ public class CPPNamespace extends PlatformObject implements ICPPNamespace, ICPPI
public void addDeclaration(IASTNode node) {
addDefinition(node);
}
public void removeDeclaration(IASTNode node) {
ArrayUtil.remove(namespaceDefinitions, node);
}
public IBinding[] getMemberBindings() {
if (namespaceDefinitions != 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -91,9 +91,6 @@ public class CPPNamespaceAlias extends PlatformObject implements ICPPNamespaceAl
}
public void addDeclaration(IASTNode node) {
}
public void removeDeclaration(IASTNode node) {
}
public IBinding[] getMemberBindings() throws DOMException {

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -123,10 +123,6 @@ public class CPPParameter extends PlatformObject implements ICPPParameter, ICPPI
}
}
public void removeDeclaration(IASTNode node) {
ArrayUtil.remove(declarations, node);
}
private IASTName getPrimaryDeclaration() {
if (declarations != null) {
for (int i = 0; i < declarations.length && declarations[i] != null; i++) {

View file

@ -78,6 +78,10 @@ abstract public class CPPScope implements ICPPScope, ICPPASTInternalScope {
@SuppressWarnings("unchecked")
public void addName(IASTName name) throws DOMException {
// don't add inactive names to the scope
if (!name.isActive())
return;
if (bindings == null)
bindings = new CharArrayObjectMap(1);
if (name instanceof ICPPASTQualifiedName) {

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -97,14 +97,6 @@ public abstract class CPPSpecialization extends PlatformObject implements ICPPSp
}
}
public void removeDeclaration(IASTNode node) {
if (node == definition) {
definition = null;
return;
}
ArrayUtil.remove(declarations, node);
}
public String getName() {
return specialized.getName();
}

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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -36,6 +36,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
import org.eclipse.cdt.core.parser.util.ArrayUtil;
import org.eclipse.cdt.core.parser.util.ObjectMap;
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.ASTNode;
import org.eclipse.cdt.internal.core.dom.parser.ProblemBinding;
import org.eclipse.cdt.internal.core.dom.parser.cpp.semantics.CPPTemplates;
@ -238,14 +239,6 @@ public abstract class CPPTemplateDefinition extends PlatformObject implements IC
}
}
public void removeDeclaration(IASTNode node) {
if (definition == node) {
definition = null;
return;
}
ArrayUtil.remove(declarations, node);
}
public IBinding resolveTemplateParameter(ICPPTemplateParameter templateParameter) {
int pos= templateParameter.getParameterPosition();
@ -298,9 +291,7 @@ public abstract class CPPTemplateDefinition extends PlatformObject implements IC
IBinding b= oName.resolvePreBinding();
IASTName n = CPPTemplates.getTemplateParameterName(updateParams[k]);
n.setBinding(b);
if (b instanceof ICPPInternalBinding) {
((ICPPInternalBinding) b).addDeclaration(n);
}
ASTInternal.addDeclaration(b, n);
}
}
}

View file

@ -198,9 +198,6 @@ public abstract class CPPTemplateParameter extends PlatformObject
}
}
}
public void removeDeclaration(IASTNode node) {
ArrayUtil.remove(declarations, node);
}
public ILinkage getLinkage() {
return Linkage.CPP_LINKAGE;

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -190,10 +190,6 @@ public class CPPTypedef extends PlatformObject implements ITypedef, ITypeContain
}
}
public void removeDeclaration(IASTNode node) {
ArrayUtil.remove(declarations, node);
}
public ILinkage getLinkage() {
return Linkage.CPP_LINKAGE;
}

View file

@ -57,9 +57,6 @@ public class CPPUnknownBinding extends PlatformObject
public void addDeclaration(IASTNode node) {
}
public void removeDeclaration(IASTNode node) {
}
public String[] getQualifiedName() {
return CPPVisitor.getQualifiedName(this);
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -91,9 +91,6 @@ public class CPPUsingDeclaration extends PlatformObject implements ICPPUsingDecl
}
public void addDeclaration(IASTNode node) {
}
public void removeDeclaration(IASTNode node) {
}
public ILinkage getLinkage() {

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* 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
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@ -168,14 +168,6 @@ public class CPPVariable extends PlatformObject implements ICPPVariable, ICPPInt
}
}
public void removeDeclaration(IASTNode node) {
if (node == definition) {
definition = null;
return;
}
ArrayUtil.remove(declarations, node);
}
/* (non-Javadoc)
* @see org.eclipse.cdt.internal.core.dom.parser.cpp.ICPPBinding#getDeclarations()
*/

View file

@ -269,7 +269,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
qname.addName(name);
}
if (LT(1) != IToken.tCOLONCOLON)
if (LTcatchEOF(1) != IToken.tCOLONCOLON)
break loop;
if (mustBeLast)
@ -367,7 +367,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
* Makes a fast check whether there could be template arguments.
*/
private boolean canBeTemplateArguments() throws EndOfFileException, BacktrackException {
if (LT(1) != IToken.tLT)
if (LTcatchEOF(1) != IToken.tLT)
return false;
final IToken mark= mark();
@ -1344,62 +1344,14 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
ICPPASTLinkageSpecification linkage = nodeFactory.newLinkageSpecification(spec);
if (LT(1) == IToken.tLBRACE) {
int endOffset= consume().getEndOffset();
int declOffset= -1;
while(true) {
IToken next= LAcatchEOF(1);
if (next == null) {
((ASTNode) linkage).setOffsetAndLength(offset, endOffset-offset);
throwBacktrack(createProblem(IProblem.SYNTAX_ERROR, endOffset, 0), linkage);
return null; // hint for java-compiler
}
try {
if (next.getType() == IToken.tEOC)
break;
if (next.getType() == IToken.tRBRACE) {
endOffset= consume().getEndOffset();
break;
}
final int nextOffset = next.getOffset();
declarationMark= next;
next= null; // don't hold on to the token while parsing namespaces, class bodies, etc.
IASTDeclaration d;
if (declOffset == nextOffset) {
// no progress
d= skipProblemDeclaration(declOffset);
} else {
declOffset= nextOffset;
d= declaration(DeclarationOptions.GLOBAL);
}
linkage.addDeclaration(d);
endOffset= calculateEndOffset(d);
} catch (BacktrackException bt) {
IASTDeclaration[] decls= problemDeclaration(declOffset, bt, DeclarationOptions.GLOBAL);
for (IASTDeclaration declaration : decls) {
linkage.addDeclaration(declaration);
endOffset= calculateEndOffset(declaration);
}
} catch (EndOfFileException e) {
IASTDeclaration d= skipProblemDeclaration(declOffset);
linkage.addDeclaration(d);
endOffset= calculateEndOffset(d);
break;
} finally {
declarationMark= null;
}
}
((ASTNode) linkage).setOffsetAndLength(offset, endOffset - offset);
declarationListInBraces(linkage, offset, DeclarationOptions.GLOBAL);
return linkage;
}
// single declaration
IASTDeclaration d = declaration(DeclarationOptions.GLOBAL);
linkage.addDeclaration(d);
int endOffset= calculateEndOffset(d);
((ASTNode) linkage).setOffsetAndLength(offset, endOffset-offset);
setRange(linkage, offset, calculateEndOffset(d));
return linkage;
}
@ -1636,9 +1588,32 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
((ASTNode) declspec).setOffsetAndLength(t.getOffset(), 0);
((ASTNode) decl).setOffsetAndLength(t.getOffset(), t.getLength());
return decl;
case IToken.t_public:
case IToken.t_protected:
case IToken.t_private:
if (option == DeclarationOptions.CPP_MEMBER) {
t= consume();
int key= t.getType();
int endOffset= consume(IToken.tCOLON).getEndOffset();
ICPPASTVisibilityLabel label = nodeFactory.newVisibilityLabel(token2Visibility(key));
setRange(label, t.getOffset(), endOffset);
return label;
}
break;
}
try {
return simpleDeclaration(option);
} catch (BacktrackException e) {
if (option != DeclarationOptions.CPP_MEMBER || declarationMark == null)
throw e;
backup(declarationMark);
try {
return usingDeclaration(declarationMark.getOffset());
} catch (BacktrackException e2) {
throw e; // throw original exception;
}
}
}
/**
@ -1667,54 +1642,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
if (LT(1) == IToken.tLBRACE) {
ICPPASTNamespaceDefinition ns = nodeFactory.newNamespaceDefinition(name);
endOffset= consume().getEndOffset();
int declOffset= -1;
while(true) {
IToken next= LAcatchEOF(1);
if (next == null) {
((ASTNode) ns).setOffsetAndLength(offset, endOffset-offset);
throwBacktrack(createProblem(IProblem.SYNTAX_ERROR, endOffset, 0), ns);
return null; // hint for java-compiler
}
try {
if (next.getType() == IToken.tEOC)
break;
if (next.getType() == IToken.tRBRACE) {
endOffset= consume().getEndOffset();
break;
}
final int nextOffset = next.getOffset();
declarationMark= next;
next= null; // don't hold on to the token while parsing namespaces, class bodies, etc.
IASTDeclaration d;
if (declOffset == nextOffset) {
// no progress
d= skipProblemDeclaration(declOffset);
} else {
declOffset= nextOffset;
d= declaration(DeclarationOptions.GLOBAL);
}
ns.addDeclaration(d);
endOffset= calculateEndOffset(d);
} catch (BacktrackException bt) {
IASTDeclaration[] decls= problemDeclaration(declOffset, bt, DeclarationOptions.GLOBAL);
for (IASTDeclaration declaration : decls) {
ns.addDeclaration(declaration);
endOffset= calculateEndOffset(declaration);
}
} catch (EndOfFileException e) {
IASTDeclaration d= skipProblemDeclaration(declOffset);
ns.addDeclaration(d);
endOffset= calculateEndOffset(d);
break;
} finally {
declarationMark= null;
}
}
((ASTNode) ns).setOffsetAndLength(offset, endOffset - offset);
declarationListInBraces(ns, offset, DeclarationOptions.GLOBAL);
return ns;
}
@ -2629,7 +2557,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
throws EndOfFileException, BacktrackException, FoundAggregateInitializer {
final IASTDeclarator dtor= declarator(strategy, option);
if (option.fAllowInitializer) {
if (LT(1) == IToken.tASSIGN && LT(2) == IToken.tLBRACE)
if (LTcatchEOF(1) == IToken.tASSIGN && LTcatchEOF(2) == IToken.tLBRACE)
throw new FoundAggregateInitializer(dtor);
IASTInitializer initializer= optionalCPPInitializer(dtor);
@ -2658,7 +2586,8 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
protected IASTInitializer optionalCPPInitializer(IASTDeclarator d) throws EndOfFileException, BacktrackException {
// handle initializer
if (LT(1) == IToken.tASSIGN) {
final int lt1= LTcatchEOF(1);
if (lt1 == IToken.tASSIGN) {
consume();
try {
return initializerClause(false);
@ -2666,7 +2595,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
failParse();
throw eof;
}
} else if (LT(1) == IToken.tLPAREN) {
} else if (lt1 == IToken.tLPAREN) {
if (d instanceof IASTFunctionDeclarator && d.getNestedDeclarator() == null) {
// constructor initializer doesn't make sense for a function
// declarator,
@ -2911,8 +2840,8 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
boolean isConst = false, isVolatile = false, isRestrict = false;
IASTName name= null;
int coloncolon= LT(1) == IToken.tCOLONCOLON ? 1 : 0;
loop: while (LT(coloncolon+1) == IToken.tIDENTIFIER) {
switch(LT(coloncolon+2)) {
loop: while (LTcatchEOF(coloncolon+1) == IToken.tIDENTIFIER) {
switch(LTcatchEOF(coloncolon+2)) {
case IToken.tCOLONCOLON:
coloncolon+= 2;
break;
@ -2936,14 +2865,14 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
return;
}
}
if (LT(1) != IToken.tSTAR) {
if (LTcatchEOF(1) != IToken.tSTAR) {
backup(mark);
return;
}
int endOffset= consume().getEndOffset();
loop: for (;;) {
switch (LT(1)) {
switch (LTcatchEOF(1)) {
case IToken.t_const:
endOffset= consume().getEndOffset();
isConst = true;
@ -2995,7 +2924,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
throws EndOfFileException, BacktrackException {
IASTDeclarator result= null;
loop: while(true) {
final int lt1= LT(1);
final int lt1= LTcatchEOF(1);
switch (lt1) {
case IToken.tLPAREN:
if (option.fAllowFunctions && strategy == DtorStrategy.PREFER_FUNCTION) {
@ -3040,7 +2969,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
endOffset= calculateEndOffset(result);
}
if (LT(1) == IToken.t_asm) { // asm labels bug 226121
if (LTcatchEOF(1) == IToken.t_asm) { // asm labels bug 226121
consume();
endOffset= asmExpression(null).getEndOffset();
@ -3267,80 +3196,14 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
throwBacktrack(errorPoint);
}
mark= null; // don't hold on to tokens while parsing the members.
int endOffset= consume().getEndOffset();
final char[] outerName= currentClassName;
currentClassName= name.getLookupKey();
try {
int declOffset= -1;
loop: while (true) {
BacktrackException origBackTrack= null;
try {
IToken next= LAcatchEOF(1);
if (next == null || next.getType() == IToken.tEOC)
break loop; // the missing semicolon will cause a problem, just break the loop.
if (next.getType() == IToken.tRBRACE) {
endOffset= consume().getEndOffset();
break loop;
}
final int nextOffset = next.getOffset();
declarationMark= next;
next= null; // don't hold on to the token while parsing namespaces, class bodies, etc.
IASTDeclaration d;
if (declOffset == nextOffset) {
// no progress
d= skipProblemDeclaration(declOffset);
} else {
declOffset= nextOffset;
switch (LT(1)) {
case IToken.t_public:
case IToken.t_protected:
case IToken.t_private:
int key= consume().getType();
endOffset= consume(IToken.tCOLON).getEndOffset();
ICPPASTVisibilityLabel label = nodeFactory.newVisibilityLabel(token2Visibility(key));
((ASTNode) label).setOffsetAndLength(declOffset, endOffset - declOffset);
astClassSpecifier.addMemberDeclaration(label);
continue loop;
}
try {
d= declaration(DeclarationOptions.CPP_MEMBER);
} catch (BacktrackException e) {
if (declarationMark == null)
throw e;
origBackTrack= new BacktrackException(e);
backup(declarationMark);
d= usingDeclaration(declarationMark.getOffset());
}
}
astClassSpecifier.addMemberDeclaration(d);
endOffset= calculateEndOffset(d);
} catch (BacktrackException bt) {
if (origBackTrack != null) {
bt= origBackTrack;
}
IASTDeclaration[] decls= problemDeclaration(declOffset, bt, DeclarationOptions.CPP_MEMBER);
for (IASTDeclaration declaration : decls) {
astClassSpecifier.addMemberDeclaration(declaration);
endOffset= calculateEndOffset(declaration);
}
} catch (EndOfFileException e) {
astClassSpecifier.addMemberDeclaration(skipProblemDeclaration(declOffset));
endOffset= eofOffset;
break loop;
} finally {
declarationMark= null;
}
}
declarationListInBraces(astClassSpecifier, offset, DeclarationOptions.CPP_MEMBER);
} finally {
currentClassName= outerName;
}
((ASTNode) astClassSpecifier).setOffsetAndLength(offset, endOffset - offset);
return astClassSpecifier;
}
@ -3501,19 +3364,19 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser {
protected IASTStatement catchBlockCompoundStatement() throws BacktrackException, EndOfFileException {
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE) {
IToken curr = LA(1);
if (mode == ParserMode.QUICK_PARSE || mode == ParserMode.STRUCTURAL_PARSE || !isActiveCode()) {
int offset = LA(1).getOffset();
IToken last = skipOverCompoundStatement();
IASTCompoundStatement cs = nodeFactory.newCompoundStatement();
((ASTNode) cs).setOffsetAndLength(curr.getOffset(), last.getEndOffset() - curr.getOffset());
setRange(cs, offset, last.getEndOffset());
return cs;
} else if (mode == ParserMode.COMPLETION_PARSE || mode == ParserMode.SELECTION_PARSE) {
if (scanner.isOnTopContext())
return compoundStatement();
IToken curr = LA(1);
int offset = LA(1).getOffset();
IToken last = skipOverCompoundStatement();
IASTCompoundStatement cs = nodeFactory.newCompoundStatement();
((ASTNode) cs).setOffsetAndLength(curr.getOffset(), last.getEndOffset() - curr.getOffset());
setRange(cs, offset, last.getEndOffset());
return cs;
}
return compoundStatement();

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
* 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:
* IBM Corporation - initial API and implementation
* Andrew Niefer (IBM Corporation) - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.internal.core.dom.parser.cpp;
@ -14,19 +14,15 @@ import org.eclipse.cdt.core.dom.ast.IASTNode;
import org.eclipse.cdt.core.dom.ast.cpp.ICPPBinding;
/**
* @author aniefer
* Non api methods for cpp bindings.
*/
public interface ICPPInternalBinding extends ICPPBinding {
//methods required by the CPPVisitor but not meant for the public interface
//implementors should keep the node with the lowest offset in declarations[0]
IASTNode [] getDeclarations();
IASTNode getDefinition();
/**
* @param declarator
*/
void addDefinition( IASTNode node );
void addDeclaration( IASTNode node );
void removeDeclaration(IASTNode node);
//implementors should keep the node with the lowest offset in declarations[0]
IASTNode[] getDeclarations();
void addDefinition(IASTNode node);
void addDeclaration(IASTNode node);
}

View file

@ -422,9 +422,15 @@ public class CPPSemantics {
}
}
if (binding != null && !(binding instanceof IProblemBinding)) {
if (binding instanceof IFunction && !(binding instanceof IProblemBinding)) {
if (data.forFunctionDeclaration()) {
addDefinition(binding, data.astName);
IASTNode node = data.astName.getParent();
if (node instanceof ICPPASTQualifiedName)
node = node.getParent();
if (node instanceof ICPPASTFunctionDeclarator
&& node.getParent() instanceof IASTFunctionDefinition) {
ASTInternal.addDefinition(binding, node);
}
}
}
// If we're still null...
@ -1483,18 +1489,6 @@ public class CPPSemantics {
}
}
private static void addDefinition(IBinding binding, IASTName name) {
if (binding instanceof IFunction) {
IASTNode node = name.getParent();
if (node instanceof ICPPASTQualifiedName)
node = node.getParent();
if (node instanceof ICPPASTFunctionDeclarator && node.getParent() instanceof IASTFunctionDefinition) {
if (binding instanceof ICPPInternalBinding)
((ICPPInternalBinding)binding).addDefinition(node);
}
}
}
public static IBinding resolveAmbiguities(IASTName name, Object[] bindings) {
bindings = ArrayUtil.trim(Object.class, bindings);
if (bindings == null || bindings.length == 0) {

View file

@ -88,6 +88,7 @@ import org.eclipse.cdt.core.parser.util.CharArraySet;
import org.eclipse.cdt.core.parser.util.CharArrayUtils;
import org.eclipse.cdt.core.parser.util.ObjectMap;
import org.eclipse.cdt.internal.core.dom.parser.ASTAmbiguousNode;
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.IASTInternalScope;
import org.eclipse.cdt.internal.core.dom.parser.ITypeContainer;
@ -591,9 +592,9 @@ public class CPPTemplates {
result= instantiate(classTemplate, args);
if (result instanceof ICPPInternalBinding) {
if (isDecl) {
((ICPPInternalBinding) result).addDeclaration(id);
ASTInternal.addDeclaration(result, id);
} else if (isDef) {
((ICPPInternalBinding) result).addDefinition(id);
ASTInternal.addDefinition(result, id);
}
}
}

View file

@ -354,9 +354,7 @@ public class CPPVisitor extends ASTQueries {
}
if (binding instanceof IIndexBinding && binding instanceof ICPPClassType) {
binding= ((CPPASTTranslationUnit) elabType.getTranslationUnit()).mapToAST((ICPPClassType) binding);
if (binding instanceof ICPPInternalBinding) {
((ICPPInternalBinding) binding).addDeclaration(elabType);
}
ASTInternal.addDeclaration(binding, elabType);
}
if (binding != null &&
@ -392,7 +390,7 @@ public class CPPVisitor extends ASTQueries {
if (scope != null) {
binding = scope.getBinding(elabType.getName(), false);
}
if (!(binding instanceof ICPPInternalBinding) || !(binding instanceof ICPPClassType)) {
if (!(binding instanceof ICPPInternalBinding) || !(binding instanceof ICPPClassType) && name.isActive()) {
if (elabType.getKind() != IASTElaboratedTypeSpecifier.k_enum) {
if (template)
binding = new CPPClassTemplate(name);
@ -403,7 +401,7 @@ public class CPPVisitor extends ASTQueries {
}
} else {
if ((binding instanceof ICPPClassTemplate) == template) {
((ICPPInternalBinding) binding).addDeclaration(elabType);
ASTInternal.addDeclaration(binding, elabType);
} else {
binding = new ProblemBinding(name, IProblemBinding.SEMANTIC_INVALID_REDECLARATION);
}
@ -435,20 +433,19 @@ public class CPPVisitor extends ASTQueries {
}
if (name.getLookupKey().length > 0 && scope != null) // can't lookup anonymous things
binding = scope.getBinding(name, false);
if (!(binding instanceof ICPPInternalBinding) || !(binding instanceof ICPPClassType)) {
if (binding instanceof ICPPInternalBinding && binding instanceof ICPPClassType && name.isActive()) {
ICPPInternalBinding internal = (ICPPInternalBinding) binding;
if (internal.getDefinition() == null && (binding instanceof ICPPClassTemplate) == template) {
ASTInternal.addDefinition(internal, compType);
} else {
binding = new ProblemBinding(name, IProblemBinding.SEMANTIC_INVALID_REDEFINITION);
}
} else {
if (template) {
binding = new CPPClassTemplate(name);
} else {
binding = new CPPClassType(name, binding);
}
} else {
ICPPInternalBinding internal = (ICPPInternalBinding) binding;
if (internal.getDefinition() == null &&
(binding instanceof ICPPClassTemplate) == template) {
internal.addDefinition(compType);
} else {
binding = new ProblemBinding(name, IProblemBinding.SEMANTIC_INVALID_REDEFINITION);
}
}
} catch (DOMException e) {
binding = e.getProblem();
@ -539,11 +536,10 @@ public class CPPVisitor extends ASTQueries {
ICPPASTTemplateDeclaration tmplDecl= CPPTemplates.getTemplateDeclaration(name);
if (tmplDecl instanceof ICPPASTTemplateSpecialization) {
IBinding b= CPPSemantics.resolveBinding(name);
if (b instanceof ICPPInternalBinding) {
if (parent instanceof ICPPASTFunctionDefinition)
((ICPPInternalBinding) b).addDefinition(name);
else
((ICPPInternalBinding) b).addDeclaration(name);
if (parent instanceof ICPPASTFunctionDefinition) {
ASTInternal.addDefinition(b, name);
} else {
ASTInternal.addDeclaration(b, name);
}
return b;
}
@ -625,13 +621,12 @@ public class CPPVisitor extends ASTQueries {
}
} else if (simpleDecl != null &&
simpleDecl.getDeclSpecifier().getStorageClass() == IASTDeclSpecifier.sc_typedef) {
if (binding instanceof ICPPInternalBinding && binding instanceof ITypedef) {
if (binding instanceof ICPPInternalBinding && binding instanceof ITypedef && name.isActive()) {
try {
IType t1 = ((ITypedef) binding).getType();
IType t2 = createType(declarator);
if (t1 != null && t2 != null && t1.isSameType(t2)) {
ICPPInternalBinding internal = (ICPPInternalBinding) binding;
internal.addDeclaration(name);
ASTInternal.addDeclaration(binding, name);
return binding;
}
} catch (DOMException e1) {
@ -646,14 +641,14 @@ public class CPPVisitor extends ASTQueries {
td.setType(targetType);
binding = td;
} else if (funcDeclarator != null) {
if (binding instanceof ICPPInternalBinding && binding instanceof IFunction) {
if (binding instanceof ICPPInternalBinding && binding instanceof IFunction && name.isActive()) {
IFunction function = (IFunction) binding;
if (CPPSemantics.isSameFunction(function, funcDeclarator)) {
ICPPInternalBinding internal = (ICPPInternalBinding) function;
if (parent instanceof IASTSimpleDeclaration) {
internal.addDeclaration(name);
ASTInternal.addDeclaration(internal, name);
} else if (internal.getDefinition() == null) {
internal.addDefinition(name);
ASTInternal.addDefinition(internal, name);
} else {
IASTNode def = internal.getDefinition();
if (def instanceof IASTDeclarator)
@ -690,8 +685,7 @@ public class CPPVisitor extends ASTQueries {
}
if (t1 != null && t2 != null) {
if (t1.isSameType(t2)) {
if (binding instanceof ICPPInternalBinding)
((ICPPInternalBinding) binding).addDeclaration(name);
ASTInternal.addDeclaration(binding, name);
} else {
binding = new ProblemBinding(name, IProblemBinding.SEMANTIC_INVALID_REDECLARATION);
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2007, 2008 Wind River Systems, Inc. and others.
* Copyright (c) 2007, 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
@ -103,4 +103,8 @@ public class ASTLiteralNode implements IASTNode {
public IASTNode copy() {
throw new UnsupportedOperationException();
}
public boolean isActive() {
return true;
}
}

View file

@ -224,7 +224,6 @@ class ASTPragma extends ASTDirectiveWithCondition implements IASTPreprocessorPra
class ASTInclusionStatement extends ASTPreprocessorNode implements IASTPreprocessorIncludeStatement {
private final ASTPreprocessorName fName;
private final String fPath;
private final boolean fIsActive;
private final boolean fIsResolved;
private final boolean fIsSystemInclude;
private final boolean fFoundByHeuristics;
@ -235,10 +234,12 @@ class ASTInclusionStatement extends ASTPreprocessorNode implements IASTPreproces
super(parent, IASTTranslationUnit.PREPROCESSOR_STATEMENT, startNumber, endNumber);
fName= new ASTPreprocessorName(this, IASTPreprocessorIncludeStatement.INCLUDE_NAME, nameStartNumber, nameEndNumber, headerName, null);
fPath= filePath == null ? "" : filePath; //$NON-NLS-1$
fIsActive= active;
fIsResolved= filePath != null;
fIsSystemInclude= !userInclude;
fFoundByHeuristics= heuristic;
if (!active) {
setInactive();
}
}
public IASTName getName() {
@ -249,10 +250,6 @@ class ASTInclusionStatement extends ASTPreprocessorNode implements IASTPreproces
return fPath;
}
public boolean isActive() {
return fIsActive;
}
public boolean isResolved() {
return fIsResolved;
}
@ -361,6 +358,7 @@ class ASTMacroDefinition extends ASTPreprocessorNode implements IASTPreprocessor
return getName().toString() + '=' + getExpansion();
}
@Override
final public boolean isActive() {
return fActive;
}
@ -433,20 +431,16 @@ class ASTFunctionStyleMacroDefinition extends ASTMacroDefinition implements IAST
class ASTUndef extends ASTPreprocessorNode implements IASTPreprocessorUndefStatement {
private final ASTPreprocessorName fName;
private final boolean fActive;
public ASTUndef(IASTTranslationUnit parent, char[] name, int startNumber, int nameNumber, int nameEndNumber, IBinding binding, boolean isActive) {
super(parent, IASTTranslationUnit.PREPROCESSOR_STATEMENT, startNumber, nameEndNumber);
fName= new ASTPreprocessorName(this, IASTPreprocessorStatement.MACRO_NAME, nameNumber, nameEndNumber, name, binding);
fActive= isActive;
if (!isActive)
setInactive();
}
public ASTPreprocessorName getMacroName() {
return fName;
}
public boolean isActive() {
return fActive;
}
}
class ASTInclusionNode implements IASTInclusionNode {

View file

@ -611,6 +611,11 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
}
}
public int getCodeBranchNesting() {
return fCurrentContext.getCodeBranchNesting();
}
private void appendStringContent(StringBuffer buf, Token t1) {
final char[] image= t1.getCharImage();
final int length= image.length;
@ -1296,7 +1301,7 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
} else {
fLocationMap.encounterPoundIfdef(offset, nameOffset, nameEndOffset, endOffset, isActive, macro);
}
return fCurrentContext.setBranchState(conditional, isActive, withinExpansion);
return fCurrentContext.setBranchState(conditional, isActive, withinExpansion, offset);
}
private CodeState executeIf(Lexer lexer, int startOffset, boolean isElif, boolean withinExpansion) throws OffsetLimitReachedException {
@ -1339,7 +1344,7 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
} else {
fLocationMap.encounterPoundIf(startOffset, condOffset, condEndOffset, endOffset, isActive, refs);
}
return fCurrentContext.setBranchState(cond, isActive, withinExpansion);
return fCurrentContext.setBranchState(cond, isActive, withinExpansion, startOffset);
}
private CodeState executeElse(final Lexer lexer, final int startOffset,boolean withinExpansion)
@ -1353,7 +1358,7 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
final boolean isActive= cond.canHaveActiveBranch(withinExpansion);
fLocationMap.encounterPoundElse(startOffset, endOffset, isActive);
return fCurrentContext.setBranchState(cond, isActive, withinExpansion);
return fCurrentContext.setBranchState(cond, isActive, withinExpansion, startOffset);
}
private CodeState executeEndif(Lexer lexer, int startOffset, boolean withinExpansion) throws OffsetLimitReachedException {
@ -1364,7 +1369,7 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
} else {
fLocationMap.encounterPoundEndIf(startOffset, endOffset);
}
return fCurrentContext.getCodeState();
return fCurrentContext.setBranchEndState(cond, withinExpansion, startOffset);
}
/**

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.internal.core.parser.scanner;
import org.eclipse.cdt.core.parser.IInactiveCodeToken;
/**
* Special token to separate active from inactive code
*/
public class InactiveCodeToken extends Token implements IInactiveCodeToken {
private int fOldNesting;
private int fNewNesting;
InactiveCodeToken(int kind, int oldNesting, int newNesting, int offset) {
super(kind, null, offset, offset);
fOldNesting= oldNesting;
fNewNesting= newNesting;
}
public int getOldNesting() {
return fOldNesting;
}
public int getNewNesting() {
return fNewNesting;
}
}

View file

@ -116,8 +116,6 @@ final class ScannerContext {
// an #end just pops one construct and restores state
if (branchKind == BranchKind.eEnd) {
result= fConditionals.remove(pos);
// implicit state change
changeState(result.fInitialState, withinExpansion);
return result;
}
@ -131,20 +129,20 @@ final class ScannerContext {
return result;
}
private void changeState(CodeState state, boolean withinExpansion) {
private void changeState(CodeState state, BranchKind kind, boolean withinExpansion, int offset) {
if (!withinExpansion) {
switch (state) {
case eActive:
if (fCurrentState == CodeState.eParseInactive)
stopInactive();
stopInactive(offset, kind);
break;
case eParseInactive:
switch (fCurrentState) {
case eActive:
startInactive();
startInactive(offset, kind);
break;
case eParseInactive:
separateInactive();
separateInactive(offset, kind);
break;
case eSkipInactive:
assert false; // in macro expansions, only.
@ -159,26 +157,35 @@ final class ScannerContext {
fCurrentState= state;
}
private void startInactive() {
if (fTokens != null && fTokens.getType() == IToken.tINACTIVE_CODE_END) {
fTokens= new Token(IToken.tINACTIVE_CODE_SEPARATOR, null, 0, 0);
} else {
fTokens= new Token(IToken.tINACTIVE_CODE_START, null, 0, 0);
}
private void startInactive(int offset, BranchKind kind) {
final int nesting = getCodeBranchNesting();
final int oldNesting = getOldNestingLevel(kind, nesting);
fTokens= new InactiveCodeToken(IToken.tINACTIVE_CODE_START, oldNesting, nesting, offset);
}
private void separateInactive() {
if (fTokens == null) {
fTokens= new Token(IToken.tINACTIVE_CODE_SEPARATOR, null, 0, 0);
}
private void separateInactive(int offset, BranchKind kind) {
final int nesting = getCodeBranchNesting();
final int oldNesting = getOldNestingLevel(kind, nesting);
fTokens= new InactiveCodeToken(IToken.tINACTIVE_CODE_SEPARATOR, oldNesting, nesting, offset);
}
private void stopInactive() {
if (fTokens != null && fTokens.getType() == IToken.tINACTIVE_CODE_START) {
fTokens= null;
} else {
fTokens= new Token(IToken.tINACTIVE_CODE_END, null, 0, 0);
private int getOldNestingLevel(BranchKind kind, int nesting) {
switch(kind) {
case eIf:
return nesting-1;
case eElif:
case eElse:
return nesting;
case eEnd:
return nesting+1;
}
return nesting;
}
private void stopInactive(int offset, BranchKind kind) {
final int nesting = getCodeBranchNesting();
final int oldNesting = getOldNestingLevel(kind, nesting);
fTokens= new InactiveCodeToken(IToken.tINACTIVE_CODE_END, oldNesting, nesting, offset);
}
public CodeState getCodeState() {
@ -188,7 +195,7 @@ final class ScannerContext {
/**
* The preprocessor has to inform the context about the state of if- and elif- branches
*/
public CodeState setBranchState(Conditional cond, boolean isActive, boolean withinExpansion) {
public CodeState setBranchState(Conditional cond, boolean isActive, boolean withinExpansion, int offset) {
CodeState newState;
if (isActive) {
cond.fTakeElse= false;
@ -198,7 +205,17 @@ final class ScannerContext {
} else {
newState= fInactiveState;
}
changeState(newState, withinExpansion);
changeState(newState, cond.fLast, withinExpansion, offset);
return newState;
}
/**
* The preprocessor has to inform the context about the state of if- and elif- branches
*/
public CodeState setBranchEndState(Conditional cond, boolean withinExpansion, int offset) {
// implicit state change
CodeState newState = cond.fInitialState;
changeState(newState, BranchKind.eEnd, withinExpansion, offset);
return newState;
}
@ -244,4 +261,13 @@ final class ScannerContext {
public void clearInactiveCodeMarkerToken() {
fTokens= null;
}
/**
* Returns the current nesting within code branches
*/
public int getCodeBranchNesting() {
if (fConditionals == null)
return 0;
return fConditionals.size();
}
}

View file

@ -316,8 +316,7 @@ abstract public class PDOMWriter {
}
}
}
} else if ((stmt instanceof IASTPreprocessorUndefStatement && ((IASTPreprocessorUndefStatement) stmt).isActive())
|| (stmt instanceof IASTPreprocessorMacroDefinition && ((IASTPreprocessorMacroDefinition) stmt).isActive())) {
} else if (stmt.isActive() && (stmt instanceof IASTPreprocessorUndefStatement || stmt instanceof IASTPreprocessorMacroDefinition)) {
IASTFileLocation sourceLoc = stmt.getFileLocation();
if (sourceLoc != null) { // skip built-ins and command line macros
IIndexFileLocation path2 = fResolver.resolveASTPath(sourceLoc.getFileName());

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2007, 2008 Wind River Systems, Inc. and others.
* Copyright (c) 2007, 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
@ -214,6 +214,10 @@ public class PDOMASTAdapter {
return fDelegate.isFrozen();
}
public boolean isActive() {
return fDelegate.isFrozen();
}
public IASTName copy() {
throw new UnsupportedOperationException();
}

View file

@ -38,12 +38,14 @@ public class CompletionTest_MacroRef_NoPrefix extends CompletionProposalsBaseTe
"__TIME__",
"__builtin_constant_p(exp)",
"__builtin_va_arg(ap, type)",
"__builtin_offsetof(T, m)",
"__builtin_types_compatible_p(x, y)",
"__complex__",
"__cplusplus",
"__extension__",
"__imag__",
"__null",
"__offsetof__(x)",
"__real__",
"__stdcall",
"__thread",

View file

@ -369,11 +369,13 @@ public class CompletionTests_PlainC extends AbstractContentAssistTest {
"__TIME__",
"__builtin_constant_p(exp)",
"__builtin_va_arg(ap, type)",
"__builtin_offsetof(T, m)",
"__builtin_types_compatible_p(x, y)",
"__complex__",
"__extension__",
"__imag__",
"__null",
"__offsetof__(x)",
"__real__",
"__stdcall",
"__thread",

View file

@ -1,5 +1,5 @@
###############################################################################
# Copyright (c) 2000, 2008 IBM Corporation and others.
# Copyright (c) 2000, 2009 IBM Corporation 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
@ -38,6 +38,10 @@ MemberFilterActionGroup.hide_nonpublic.label=Hide Non-&Public Members
MemberFilterActionGroup.hide_nonpublic.tooltip=Hide Non-Public Members
MemberFilterActionGroup.hide_nonpublic.description=Toggles the visibility of non-public members
MemberFilterActionGroup.hide_inactive.label=Hide &Inactive Elements
MemberFilterActionGroup.hide_inactive.tooltip=Hide Inactive Elements
MemberFilterActionGroup.hide_inactive.description=Toggles the visibility of inactive elements
ActionUtil.notOnBuildPath.title=Operation Cannot be Performed
ActionUtil.notOnBuildPath.message=The resource is not on the build path of a Java project.

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2001, 2008 IBM Corporation and others.
* Copyright (c) 2001, 2009 IBM Corporation 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
@ -11,13 +11,15 @@
*******************************************************************************/
package org.eclipse.cdt.internal.ui.viewsupport;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.jface.viewers.ViewerFilter;
import org.eclipse.cdt.core.model.CModelException;
import org.eclipse.cdt.core.model.IDeclaration;
import org.eclipse.cdt.core.model.IField;
import org.eclipse.cdt.core.model.IMember;
import org.eclipse.cdt.core.model.ISourceReference;
import org.eclipse.cdt.core.parser.ast.ASTAccessVisibility;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.jface.viewers.ViewerFilter;
/**
@ -30,6 +32,8 @@ public class MemberFilter extends ViewerFilter{
public static final int FILTER_NONPUBLIC= 1;
public static final int FILTER_STATIC= 2;
public static final int FILTER_FIELDS= 4;
public static final int FILTER_INACTIVE= 0x10;
/** @deprecated Unsupported filter constant */
@Deprecated
public static final int FILTER_LOCALTYPES= 8;
@ -86,6 +90,11 @@ public class MemberFilter extends ViewerFilter{
// ignore
}
}
if (hasFilter(FILTER_INACTIVE)) {
if (element instanceof ISourceReference && !((ISourceReference) element).isActive()) {
return false;
}
}
return true;
}
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2001, 2008 IBM Corporation and others.
* Copyright (c) 2001, 2009 IBM Corporation 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
@ -12,6 +12,7 @@ package org.eclipse.cdt.internal.ui.viewsupport;
import org.eclipse.jface.action.Action;
import org.eclipse.ui.PlatformUI;
import org.eclipse.cdt.ui.actions.MemberFilterActionGroup;
/**
@ -28,8 +29,9 @@ public class MemberFilterAction extends Action {
fFilterActionGroup= actionGroup;
fFilterProperty= property;
if (contextHelpId != null) {
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, contextHelpId);
}
setChecked(initValue);
}

View file

@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2001, 2008 IBM Corporation and others.
* Copyright (c) 2001, 2009 IBM Corporation 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
@ -29,37 +29,48 @@ package org.eclipse.cdt.ui.actions;
*/
import java.util.ArrayList;
import org.eclipse.cdt.internal.ui.viewsupport.MemberFilter;
import org.eclipse.cdt.internal.ui.viewsupport.MemberFilterAction;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.ui.PreferenceConstants;
import org.eclipse.cdt.internal.ui.actions.ActionMessages;
import org.eclipse.core.runtime.Assert;
import org.eclipse.jface.action.IMenuManager;
import org.eclipse.jface.action.IToolBarManager;
import org.eclipse.jface.preference.IPreferenceStore;
import org.eclipse.core.runtime.Assert;
import org.eclipse.jface.viewers.StructuredViewer;
import org.eclipse.swt.custom.BusyIndicator;
import org.eclipse.ui.IActionBars;
import org.eclipse.ui.IMemento;
import org.eclipse.ui.actions.ActionGroup;
import org.eclipse.cdt.internal.ui.ICHelpContextIds;
import org.eclipse.cdt.ui.CUIPlugin;
import org.eclipse.cdt.ui.PreferenceConstants;
import org.eclipse.cdt.internal.ui.CPluginImages;
import org.eclipse.cdt.internal.ui.ICHelpContextIds;
import org.eclipse.cdt.internal.ui.actions.ActionMessages;
import org.eclipse.cdt.internal.ui.viewsupport.MemberFilter;
import org.eclipse.cdt.internal.ui.viewsupport.MemberFilterAction;
public class MemberFilterActionGroup extends ActionGroup {
public static final int FILTER_NONPUBLIC= MemberFilter.FILTER_NONPUBLIC;
public static final int FILTER_STATIC= MemberFilter.FILTER_STATIC;
public static final int FILTER_FIELDS= MemberFilter.FILTER_FIELDS;
/**
* @since 5.1
*/
public static final int FILTER_INACTIVE= MemberFilter.FILTER_INACTIVE;
/** @deprecated Unsupported filter constant */
@Deprecated
public static final int FILTER_LOCALTYPES= MemberFilter.FILTER_LOCALTYPES;
/**
* @deprecated we may choose to add more filters in future versions.
*/
@Deprecated
public static final int ALL_FILTERS= FILTER_NONPUBLIC | FILTER_FIELDS | FILTER_STATIC;
private static final String TAG_HIDEFIELDS= "hidefields"; //$NON-NLS-1$
private static final String TAG_HIDESTATIC= "hidestatic"; //$NON-NLS-1$
private static final String TAG_HIDENONPUBLIC= "hidenonpublic"; //$NON-NLS-1$
private static final String TAG_HIDEINACTIVE= "hideinactive"; //$NON-NLS-1$
private MemberFilterAction[] fFilterActions;
private MemberFilter fFilter;
@ -101,6 +112,7 @@ public class MemberFilterActionGroup extends ActionGroup {
boolean doHideFields= store.getBoolean(getPreferenceKey(FILTER_FIELDS));
boolean doHideStatic= store.getBoolean(getPreferenceKey(FILTER_STATIC));
boolean doHidePublic= store.getBoolean(getPreferenceKey(FILTER_NONPUBLIC));
boolean doHideInactive= store.getBoolean(getPreferenceKey(FILTER_INACTIVE));
fFilter= new MemberFilter();
if (doHideFields)
@ -109,6 +121,8 @@ public class MemberFilterActionGroup extends ActionGroup {
fFilter.addFilter(FILTER_STATIC);
if (doHidePublic)
fFilter.addFilter(FILTER_NONPUBLIC);
if (doHideInactive)
fFilter.addFilter(FILTER_INACTIVE);
// fields
String title= ActionMessages.getString("MemberFilterActionGroup.hide_fields.label"); //$NON-NLS-1$
@ -134,8 +148,15 @@ public class MemberFilterActionGroup extends ActionGroup {
hideNonPublic.setToolTipText(ActionMessages.getString("MemberFilterActionGroup.hide_nonpublic.tooltip")); //$NON-NLS-1$
CPluginImages.setImageDescriptors(hideNonPublic, CPluginImages.T_LCL, CPluginImages.IMG_ACTION_SHOW_PUBLIC);
// inactive
title= ActionMessages.getString("MemberFilterActionGroup.hide_inactive.label"); //$NON-NLS-1$
MemberFilterAction hideInactive= new MemberFilterAction(this, title, FILTER_INACTIVE, null, doHideInactive);
hideInactive.setDescription(ActionMessages.getString("MemberFilterActionGroup.hide_inactive.description")); //$NON-NLS-1$
hideInactive.setToolTipText(ActionMessages.getString("MemberFilterActionGroup.hide_inactive.tooltip")); //$NON-NLS-1$
CPluginImages.setImageDescriptors(hideInactive, CPluginImages.T_LCL, CPluginImages.IMG_ACTION_HIDE_INACTIVE);
// order corresponds to order in toolbar
fFilterActions= new MemberFilterAction[] { hideFields, hideStatic, hideNonPublic };
fFilterActions= new MemberFilterAction[] { hideFields, hideStatic, hideNonPublic, hideInactive };
fViewer.addFilter(fFilter);
}
@ -148,9 +169,9 @@ public class MemberFilterActionGroup extends ActionGroup {
* the last used filter settings in the preference store
* @param inViewMenu if <code>true</code> the actions are added to the view
* menu. If <code>false</code> they are added to the toobar.
* @param availableFilters Specifies which filter action should be contained. <code>FILTER_NONPUBLIC</code>,
* <code>FILTER_STATIC</code> and <code>FILTER_FIELDS</code>
* or a combination of these constants are possible values. Use <code>ALL_FILTERS</code> to select all available filters.
* @param availableFilters Specifies which filter action should be contained. {@link #FILTER_NONPUBLIC},
* {@link #FILTER_STATIC}, {@link #FILTER_FIELDS}, {@link #FILTER_INACTIVE}
* or a combination of these constants are possible values.
*/
public MemberFilterActionGroup(StructuredViewer viewer, String viewerId, boolean inViewMenu, int availableFilters) {
@ -212,6 +233,21 @@ public class MemberFilterActionGroup extends ActionGroup {
actions.add(hideNonPublic);
}
// non-public
filterProperty= FILTER_INACTIVE;
if (isSet(filterProperty, availableFilters)) {
boolean filterEnabled= store.getBoolean(getPreferenceKey(filterProperty));
if (filterEnabled) {
fFilter.addFilter(filterProperty);
}
title= ActionMessages.getString("MemberFilterActionGroup.hide_inactive.label"); //$NON-NLS-1$
MemberFilterAction hideInactive= new MemberFilterAction(this, title, filterProperty, null, filterEnabled);
hideInactive.setDescription(ActionMessages.getString("MemberFilterActionGroup.hide_inactive.description")); //$NON-NLS-1$
hideInactive.setToolTipText(ActionMessages.getString("MemberFilterActionGroup.hide_inactive.tooltip")); //$NON-NLS-1$
CPluginImages.setImageDescriptors(hideInactive, CPluginImages.T_LCL, "filterInactive.gif"); //$NON-NLS-1$
actions.add(hideInactive);
}
// order corresponds to order in toolbar
fFilterActions= actions.toArray(new MemberFilterAction[actions.size()]);
@ -230,7 +266,7 @@ public class MemberFilterActionGroup extends ActionGroup {
* Sets the member filters.
*
* @param filterProperty the filter to be manipulated. Valid values are <code>FILTER_FIELDS</code>,
* <code>FILTER_PUBLIC</code>, and <code>FILTER_PRIVATE</code> as defined by this action
* <code>FILTER_PUBLIC</code>, <code>FILTER_PRIVATE</code> and <code>FILTER_INACTIVE</code> as defined by this action
* group
* @param set if <code>true</code> the given filter is installed. If <code>false</code> the
* given filter is removed
@ -278,8 +314,8 @@ public class MemberFilterActionGroup extends ActionGroup {
* Returns <code>true</code> if the given filter is installed.
*
* @param filterProperty the filter to be tested. Valid values are <code>FILTER_FIELDS</code>,
* <code>FILTER_PUBLIC</code>, and <code>FILTER_PRIVATE</code> as defined by this action
* group
* <code>FILTER_PUBLIC</code>, <code>FILTER_PRIVATE</code> and <code>FILTER_INACTIVE</code>
* as defined by this action group
*/
public boolean hasMemberFilter(int filterProperty) {
return fFilter.hasFilter(filterProperty);
@ -294,6 +330,7 @@ public class MemberFilterActionGroup extends ActionGroup {
memento.putString(TAG_HIDEFIELDS, String.valueOf(hasMemberFilter(FILTER_FIELDS)));
memento.putString(TAG_HIDESTATIC, String.valueOf(hasMemberFilter(FILTER_STATIC)));
memento.putString(TAG_HIDENONPUBLIC, String.valueOf(hasMemberFilter(FILTER_NONPUBLIC)));
memento.putString(TAG_HIDEINACTIVE, String.valueOf(hasMemberFilter(FILTER_INACTIVE)));
}
/**
@ -305,11 +342,12 @@ public class MemberFilterActionGroup extends ActionGroup {
*/
public void restoreState(IMemento memento) {
setMemberFilters(
new int[] {FILTER_FIELDS, FILTER_STATIC, FILTER_NONPUBLIC},
new int[] {FILTER_FIELDS, FILTER_STATIC, FILTER_NONPUBLIC, FILTER_INACTIVE},
new boolean[] {
Boolean.valueOf(memento.getString(TAG_HIDEFIELDS)).booleanValue(),
Boolean.valueOf(memento.getString(TAG_HIDESTATIC)).booleanValue(),
Boolean.valueOf(memento.getString(TAG_HIDENONPUBLIC)).booleanValue()
Boolean.valueOf(memento.getString(TAG_HIDENONPUBLIC)).booleanValue(),
Boolean.valueOf(memento.getString(TAG_HIDEINACTIVE)).booleanValue()
}, false);
}
@ -332,6 +370,7 @@ public class MemberFilterActionGroup extends ActionGroup {
tbm.add(fFilterActions[0]); // fields
tbm.add(fFilterActions[1]); // static
tbm.add(fFilterActions[2]); // public
tbm.add(fFilterActions[3]); // inactive
}
/**
@ -348,10 +387,12 @@ public class MemberFilterActionGroup extends ActionGroup {
menu.prependToGroup(filters, fFilterActions[0]); // fields
menu.prependToGroup(filters, fFilterActions[1]); // static
menu.prependToGroup(filters, fFilterActions[2]); // public
menu.prependToGroup(filters, fFilterActions[3]); // inactive
} else {
menu.add(fFilterActions[0]); // fields
menu.add(fFilterActions[1]); // static
menu.add(fFilterActions[2]); // public
menu.add(fFilterActions[3]); // inactive
}
}