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

fix bug 70073

This commit is contained in:
Andrew Niefer 2004-08-12 19:44:54 +00:00
parent 2b19fdf07e
commit df84ae7f47
3 changed files with 121 additions and 22 deletions

View file

@ -1822,4 +1822,20 @@ public class Scanner2Test extends BaseScanner2Test
assertTrue( callback.problems.isEmpty() );
}
public void testBug70073() throws Exception
{
StringBuffer buffer = new StringBuffer( "#if CONST \n #endif \n #elif CONST \n int" ); //$NON-NLS-1$
final List problems = new ArrayList();
ISourceElementRequestor requestor = new NullSourceElementRequestor() {
public boolean acceptProblem(IProblem problem)
{
problems.add( problem );
return super.acceptProblem( problem );
}
};
initializeScanner( buffer.toString(), ParserMode.COMPLETE_PARSE, requestor );
validateToken( IToken.t_int );
assertEquals( problems.size(), 1 );
}
}

View file

@ -120,7 +120,13 @@ public class CharTable extends HashTable {
final public boolean containsKey( char[] key ){
return lookup( key ) != -1;
}
final public char[] findKey( char[] buffer, int start, int len ){
int idx = lookup( buffer, start, len );
if( idx == -1 )
return null;
return keyTable[ idx ];
}
protected int lookup(char[] buffer ){
return lookup(buffer, 0, buffer.length);
}

View file

@ -101,6 +101,16 @@ public class Scanner2 implements IScanner, IScannerData {
private int[] bufferLimit = new int[bufferInitialSize];
private int[] bufferLineNums = new int[bufferInitialSize];
//branch tracking
private int branchStackPos = -1;
private int[] branches = new int[bufferInitialSize];
//states
final static private int BRANCH_IF = 1;
final static private int BRANCH_ELIF = 2;
final static private int BRANCH_ELSE = 3;
final static private int BRANCH_END = 4;
// Utility
private static String[] emptyStringArray = new String[0];
private static char[] emptyCharArray = new char[0];
@ -1113,6 +1123,42 @@ public class Scanner2 implements IScanner, IScannerData {
return newToken( tokenType, result );
}
private boolean branchState( int state ){
if( state != BRANCH_IF && branchStackPos == -1 )
return false;
switch( state ){
case BRANCH_IF:
if( ++branchStackPos == branches.length ){
int [] temp = new int [ branches.length << 1 ];
System.arraycopy( branches, 0, temp, 0, branches.length );
}
branches[branchStackPos] = BRANCH_IF;
return true;
case BRANCH_ELIF:
case BRANCH_ELSE:
switch( branches[branchStackPos] ){
case BRANCH_IF:
case BRANCH_ELIF:
branches[branchStackPos] = state;
return true;
default:
return false;
}
case BRANCH_END:
switch( branches[branchStackPos] ){
case BRANCH_IF:
case BRANCH_ELSE:
case BRANCH_ELIF:
--branchStackPos;
return true;
default:
return false;
}
}
return false;
}
private void handlePPDirective(int pos) throws ScannerException, EndOfFileException {
char[] buffer = bufferStack[bufferStackPos];
int limit = bufferLimit[bufferStackPos];
@ -1169,6 +1215,7 @@ public class Scanner2 implements IScanner, IScannerData {
len = bufferPos[bufferStackPos] - start;
if( isLimitReached() )
handleCompletionOnExpression( CharArrayUtils.extract( buffer, start, len ) );
branchState( BRANCH_IF );
if (expressionEvaluator.evaluate(buffer, start, len, definitions) == 0) {
if (dlog != null) dlog.println("#if <FALSE> " + new String(buffer,start+1,len-1)); //$NON-NLS-1$
skipOverConditionalCode(true);
@ -1180,14 +1227,23 @@ public class Scanner2 implements IScanner, IScannerData {
case ppElse:
case ppElif:
// Condition must have been true, skip over the rest
if( branchState( type == ppElse ? BRANCH_ELSE : BRANCH_ELIF) ){
skipToNewLine();
skipOverConditionalCode(false);
} else {
handleProblem( IProblem.PREPROCESSOR_UNBALANCE_CONDITION, start, ppKeywords.findKey( buffer, start, len ) );
skipToNewLine();
}
if( isLimitReached() )
handleInvalidCompletion();
return;
case ppError:
throw new ScannerException(null);
case ppEndif:
if( !branchState( BRANCH_END ) )
handleProblem( IProblem.PREPROCESSOR_UNBALANCE_CONDITION, start, ppKeywords.findKey( buffer, start, len ) );
break;
default:
problem = true;
@ -1649,6 +1705,8 @@ public class Scanner2 implements IScanner, IScannerData {
skipToNewLine();
branchState( BRANCH_IF );
if ((definitions.get(buffer, idstart, idlen) != null) == positive) {
if (dlog != null) dlog.println((positive ? "#ifdef" : "#ifndef") //$NON-NLS-1$ //$NON-NLS-2$
+ " <TRUE> " + new String(buffer, idstart, idlen)); //$NON-NLS-1$
@ -1705,14 +1763,22 @@ public class Scanner2 implements IScanner, IScannerData {
case ppIfndef:
case ppIf:
++nesting;
branchState( BRANCH_IF );
break;
case ppElse:
if( branchState( BRANCH_ELSE ) ){
if (checkelse && nesting == 0) {
skipToNewLine();
return;
}
} else {
//problem, ignore this one.
handleProblem( IProblem.PREPROCESSOR_UNBALANCE_CONDITION, start, ppKeywords.findKey( buffer, start, len ) );
skipToNewLine();
}
break;
case ppElif:
if( branchState( BRANCH_ELIF ) ){
if (checkelse && nesting == 0) {
// check the condition
start = bufferPos[bufferStackPos];
@ -1722,14 +1788,25 @@ public class Scanner2 implements IScanner, IScannerData {
// condition passed, we're good
return;
}
} else {
//problem, ignore this one.
handleProblem( IProblem.PREPROCESSOR_UNBALANCE_CONDITION, start, ppKeywords.findKey( buffer, start, len ) );
skipToNewLine();
}
break;
case ppEndif:
if( branchState( BRANCH_END ) ){
if (nesting > 0) {
--nesting;
} else {
skipToNewLine();
return;
}
} else {
//problem, ignore this one.
handleProblem( IProblem.PREPROCESSOR_UNBALANCE_CONDITION, start, ppKeywords.findKey( buffer, start, len ) );
skipToNewLine();
}
break;
}
}