diff options
Diffstat (limited to 'core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java')
-rw-r--r-- | core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java | 84 |
1 files changed, 69 insertions, 15 deletions
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java index 0f2834e1c75..6c3d9216050 100644 --- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java +++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/dom/parser/cpp/GNUCPPSourceParser.java @@ -18,6 +18,7 @@ package org.eclipse.cdt.internal.core.dom.parser.cpp; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collections; import java.util.List; @@ -132,6 +133,7 @@ import org.eclipse.cdt.core.parser.IParserLogService; import org.eclipse.cdt.core.parser.IProblem; import org.eclipse.cdt.core.parser.IScanner; import org.eclipse.cdt.core.parser.IToken; +import org.eclipse.cdt.core.parser.Keywords; import org.eclipse.cdt.core.parser.ParserMode; import org.eclipse.cdt.core.parser.util.ArrayUtil; import org.eclipse.cdt.core.parser.util.CharArrayUtils; @@ -3295,8 +3297,7 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { * declarator ("=" initializerClause | "(" expressionList ")")? * * @return declarator that this parsing produced. - * @throws BacktrackException - * request a backtrack + * @throws BacktrackException request a backtrack * @throws FoundAggregateInitializer */ private IASTDeclarator initDeclarator(DtorStrategy strategy, IASTDeclSpecifier declspec, DeclarationOptions option) @@ -3305,18 +3306,21 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { if (option.fAllowInitializer) { final IASTDeclarator typeRelevantDtor = ASTQueries.findTypeRelevantDeclarator(dtor); if (option != DeclarationOptions.PARAMETER && typeRelevantDtor instanceof IASTFunctionDeclarator) { - // Function declarations don't have initializers - // For member functions we need to consider pure-virtual syntax - if (option == DeclarationOptions.CPP_MEMBER && LTcatchEOF(1) == IToken.tASSIGN - && LTcatchEOF(2) == IToken.tINTEGER) { - consume(); - IToken t = consume(); - char[] image = t.getCharImage(); - if (image.length != 1 || image[0] != '0') { - throwBacktrack(t); + // Function declarations don't have initializers. + // For member functions we need to consider virtual specifiers and pure-virtual syntax. + if (option == DeclarationOptions.CPP_MEMBER) { + optionalVirtSpecifierSeq((ICPPASTFunctionDeclarator) typeRelevantDtor); + int lt1 = LTcatchEOF(1); + if (lt1 == IToken.tASSIGN && LTcatchEOF(2) == IToken.tINTEGER) { + consume(); + IToken t = consume(); + char[] image = t.getCharImage(); + if (image.length != 1 || image[0] != '0') { + throwBacktrack(t); + } + ((ICPPASTFunctionDeclarator) typeRelevantDtor).setPureVirtual(true); + adjustEndOffset(dtor, t.getEndOffset()); // We can only adjust the offset of the outermost dtor. } - ((ICPPASTFunctionDeclarator) typeRelevantDtor).setPureVirtual(true); - adjustEndOffset(dtor, t.getEndOffset()); // we can only adjust the offset of the outermost dtor. } } else { if (LTcatchEOF(1) == IToken.tASSIGN && LTcatchEOF(2) == IToken.tLBRACE) @@ -3346,7 +3350,37 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { return dtor; } - /** + /** + * virt-specifier-seq + * virt-specifier + * virt-specifier-seq virt-specifier + * + * virt-specifier: + * override + * final + * @throws EndOfFileException + * @throws BacktrackException + */ + private void optionalVirtSpecifierSeq(ICPPASTFunctionDeclarator typeRelevantDtor) + throws EndOfFileException, BacktrackException { + while (true) { + IToken token = LAcatchEOF(1); + if (token.getType() != IToken.tIDENTIFIER) + break; + char[] tokenImage = token.getCharImage(); + if (Arrays.equals(Keywords.cOVERRIDE, tokenImage)) { + consume(); + typeRelevantDtor.setOverride(true); + } else if (Arrays.equals(Keywords.cFINAL, tokenImage)) { + consume(); + typeRelevantDtor.setFinal(true); + } else { + break; + } + } + } + + /** * initializer: * brace-or-equal-initializer * ( expression-list ) @@ -4070,6 +4104,11 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { ICPPASTCompositeTypeSpecifier astClassSpecifier = nodeFactory.newCompositeTypeSpecifier(classKind, name); + // class virt specifier + if(LT(1) == IToken.tIDENTIFIER) { + classVirtSpecifier(astClassSpecifier); + } + // base clause if (LT(1) == IToken.tCOLON) { baseClause(astClassSpecifier); @@ -4134,7 +4173,22 @@ public class GNUCPPSourceParser extends AbstractGNUSourceCodeParser { consume(); } } - + + /** + * Parse a class virtual specifier for a class specification. + * class-virt-specifier: + * final + * @param astClassSpecifier + */ + private void classVirtSpecifier(ICPPASTCompositeTypeSpecifier astClassSpecifier) throws EndOfFileException, BacktrackException { + IToken token = LA(); + char[] tokenImage = token.getCharImage(); + if(token.getType() == IToken.tIDENTIFIER && Arrays.equals(Keywords.cFINAL, tokenImage)){ + consume(); + astClassSpecifier.setFinal(true); + } + } + /** * base-specifier: * ::? nested-name-specifier? class-name |