mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-06-06 17:26:01 +02:00
Bug 303152: trailing empty macro expansions in IASTTranslationUnit.
This commit is contained in:
parent
290eeeff55
commit
35de77c32b
5 changed files with 53 additions and 14 deletions
|
@ -58,6 +58,7 @@ import org.eclipse.cdt.core.dom.ast.IASTNullStatement;
|
|||
import org.eclipse.cdt.core.dom.ast.IASTParameterDeclaration;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTPointerOperator;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTPreprocessorMacroDefinition;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTPreprocessorMacroExpansion;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTPreprocessorPragmaStatement;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTPreprocessorStatement;
|
||||
import org.eclipse.cdt.core.dom.ast.IASTProblem;
|
||||
|
@ -7324,4 +7325,21 @@ public class AST2Tests extends AST2BaseTest {
|
|||
parseAndCheckBindings(code, ParserLanguage.C, true);
|
||||
parseAndCheckBindings(code, ParserLanguage.CPP, true);
|
||||
}
|
||||
|
||||
// #define MACRO
|
||||
// void funca(){
|
||||
// }
|
||||
// MACRO
|
||||
public void testEmptyTrailingMacro_303152() throws Exception {
|
||||
final String code = getAboveComment();
|
||||
for (ParserLanguage lang : ParserLanguage.values()) {
|
||||
IASTTranslationUnit tu= parseAndCheckBindings(code, lang);
|
||||
IASTPreprocessorMacroExpansion[] expansions = tu.getMacroExpansions();
|
||||
assertEquals(1, expansions.length);
|
||||
IToken t= tu.getSyntax();
|
||||
while (t.getNext() != null)
|
||||
t= t.getNext();
|
||||
assertEquals("MACRO", t.getImage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2002, 2009 IBM Corporation and others.
|
||||
* Copyright (c) 2002, 2010 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
|
||||
|
@ -7,6 +7,7 @@
|
|||
*
|
||||
* Contributors:
|
||||
* John Camelon (IBM Rational Software) - Initial API and implementation
|
||||
* Markus Schorn (Wind River Systems)
|
||||
*******************************************************************************/
|
||||
package org.eclipse.cdt.core.parser;
|
||||
|
||||
|
@ -18,16 +19,21 @@ public class EndOfFileException extends Exception {
|
|||
private static final long serialVersionUID= 1607883323361197919L;
|
||||
|
||||
private final boolean fEndsInactiveCode;
|
||||
private final int fOffset;
|
||||
|
||||
public EndOfFileException() {
|
||||
fEndsInactiveCode= false;
|
||||
/**
|
||||
* @since 5.2
|
||||
*/
|
||||
public EndOfFileException(int offset) {
|
||||
this(offset, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @since 5.1
|
||||
* @since 5.2
|
||||
*/
|
||||
public EndOfFileException(boolean endsInactiveCode) {
|
||||
fEndsInactiveCode= true;
|
||||
public EndOfFileException(int offset, boolean endsInactiveCode) {
|
||||
fOffset= offset;
|
||||
fEndsInactiveCode= endsInactiveCode;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -36,4 +42,12 @@ public class EndOfFileException extends Exception {
|
|||
public boolean endsInactiveCode() {
|
||||
return fEndsInactiveCode;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the offset at which the translation unit ends, or -1 if not known.
|
||||
* @since 5.2
|
||||
*/
|
||||
public int getEndOffset() {
|
||||
return fOffset;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2002, 2009 IBM Corporation and others.
|
||||
* Copyright (c) 2002, 2010 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
|
||||
|
@ -41,6 +41,7 @@ public class OffsetLimitReachedException extends EndOfFileException {
|
|||
private final int fOrigin;
|
||||
|
||||
public OffsetLimitReachedException(int origin, IToken lastToken) {
|
||||
super(lastToken != null ? lastToken.getEndOffset() : -1);
|
||||
fOrigin= origin;
|
||||
finalToken= lastToken;
|
||||
}
|
||||
|
|
|
@ -194,6 +194,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
|
||||
private final INodeFactory nodeFactory;
|
||||
private boolean fActiveCode= true;
|
||||
private int fEndOffset= -1;
|
||||
|
||||
protected AbstractGNUSourceCodeParser(IScanner scanner,
|
||||
IParserLogService logService, ParserMode parserMode,
|
||||
|
@ -268,7 +269,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
return t;
|
||||
} catch (OffsetLimitReachedException olre) {
|
||||
if (mode != ParserMode.COMPLETION_PARSE)
|
||||
throw new EndOfFileException();
|
||||
throw new EndOfFileException(olre.getEndOffset());
|
||||
createCompletionNode(olre.getFinalToken());
|
||||
throw olre;
|
||||
}
|
||||
|
@ -418,7 +419,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
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);
|
||||
throw new EndOfFileException(t.getOffset(), true);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -428,6 +429,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
try {
|
||||
return LA(i);
|
||||
} catch (EndOfFileException e) {
|
||||
fEndOffset= e.getEndOffset();
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
@ -448,6 +450,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
try {
|
||||
return LT(i);
|
||||
} catch (EndOfFileException e) {
|
||||
fEndOffset= e.getEndOffset();
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -679,7 +682,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
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);
|
||||
throw new EndOfFileException(t.getOffset(), true);
|
||||
}
|
||||
}
|
||||
result = consume();
|
||||
|
@ -691,7 +694,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
++depth;
|
||||
break;
|
||||
case IToken.tEOC:
|
||||
throw new EndOfFileException();
|
||||
throw new EndOfFileException(result.getOffset());
|
||||
}
|
||||
}
|
||||
return result;
|
||||
|
@ -1239,7 +1242,9 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
protected void parseTranslationUnit() {
|
||||
final IASTTranslationUnit tu= getTranslationUnit();
|
||||
declarationList(tu, DeclarationOptions.GLOBAL, false, 0);
|
||||
((ASTNode) tu).setLength(getEndOffset());
|
||||
// Bug 3033152: getEndOffset() is computed off the last node and ignores trailing macros.
|
||||
final int length= Math.max(getEndOffset(), fEndOffset);
|
||||
((ASTNode) tu).setLength(length);
|
||||
}
|
||||
|
||||
protected final void declarationListInBraces(final IASTDeclarationListOwner tu, int offset, DeclarationOptions options) throws EndOfFileException, BacktrackException {
|
||||
|
@ -1312,6 +1317,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
IASTDeclaration declaration= skipProblemDeclaration(offset);
|
||||
addDeclaration(tu, declaration, active);
|
||||
if (!e.endsInactiveCode()) {
|
||||
fEndOffset= e.getEndOffset();
|
||||
break;
|
||||
}
|
||||
} finally {
|
||||
|
@ -1743,7 +1749,7 @@ public abstract class AbstractGNUSourceCodeParser implements ISourceCodeParser {
|
|||
open--;
|
||||
break;
|
||||
case IToken.tEOC:
|
||||
throw new EndOfFileException();
|
||||
throw new EndOfFileException(t.getOffset());
|
||||
|
||||
default:
|
||||
if (content != null) {
|
||||
|
|
|
@ -566,7 +566,7 @@ public class CPreprocessor implements ILexerLog, IScanner, IAdaptable {
|
|||
|
||||
case IToken.tEND_OF_INPUT:
|
||||
if (fContentAssistLimit < 0) {
|
||||
throw new EndOfFileException();
|
||||
throw new EndOfFileException(t1.getOffset());
|
||||
}
|
||||
int useType= fHandledCompletion ? IToken.tEOC : IToken.tCOMPLETION;
|
||||
int sequenceNumber= fLocationMap.getSequenceNumberForOffset(fContentAssistLimit);
|
||||
|
|
Loading…
Add table
Reference in a new issue