Always convert keywords and typedef names to identifiers when processing preprocessor expressions.

This avoids various problems with inappropriately processing these elements, which should not be recognized as such at preprocessing time. For example, the following program should compile without errors, but did not:

typedef long foo;
#if int+1
#if foo-1
int main(void) {}
#endif
#endif
This commit is contained in:
Stephen Heumann 2016-12-19 17:16:18 -06:00
parent 7fa74d1183
commit 4c0b02f32e
1 changed files with 13 additions and 0 deletions

View File

@ -218,6 +218,7 @@ type
var
dateStr: longStringPtr; {macro date string}
doingPPExpression: boolean; {are we processing a preprocessor expression?}
doingstring: boolean; {used to supress comments in strings}
errors: array[1..maxErr] of errorType; {errors in this line}
eofPtr: ptr; {points one byte past the last char in the file}
@ -1837,8 +1838,10 @@ var
{ global variable expressionValue. }
begin {NumericDirective}
doingPPExpression := true;
NextToken; {skip the directive name}
Expression(preprocessorExpression, []); {evaluate the expression}
doingPPExpression := false;
end; {NumericDirective}
@ -3308,6 +3311,7 @@ needWriteLine := false; {no lines are pending}
switchLanguages := false; {not switching languages}
lastWasReturn := false; {last char was not return}
doingstring := false; {not doing a string}
doingPPExpression := false; {not doing a preprocessor expression}
unix_1 := false; {int is 16 bits}
new(mp); {__LINE__}
@ -4045,6 +4049,15 @@ if token.kind = stringconst then {handle adjacent strings}
token := tToken;
until done;
1:
if doingPPExpression then begin
if token.class = reservedWord then begin
token.name := @reservedWords[token.kind];
token.kind := ident;
token.class := identifier;
end; {if}
if token.kind = typedef then
token.kind := ident;
end; {if}
if printMacroExpansions then {print the token stream}
PrintToken(token);
end; {NextToken}