diff options
author | 2004-06-06 23:43:49 -0700 | |
---|---|---|
committer | 2005-04-07 21:02:04 -0700 | |
commit | a38e6db49e947820217f6398affe1fa840b72241 (patch) | |
tree | 1f047d7a2fcca9ba4681dce88302e8d0a3ba8087 /token.h | |
parent | Ok, this handles all token types in token comparison, (diff) | |
download | sparse-a38e6db49e947820217f6398affe1fa840b72241.tar.gz sparse-a38e6db49e947820217f6398affe1fa840b72241.tar.bz2 sparse-a38e6db49e947820217f6398affe1fa840b72241.zip |
[PATCH] Fix preprocessor expansion anti-recursion properly
We taint identifiers when we are done with argument expansion; we
untaint them when scan gets through the "untaint" token we leave right
after the body of macro; we mark tokens noexpand in three situations:
1) when we copy a token marked noexpand;
2) when we get to expanding a token and see that its identifier is
currently tainted;
3) when we scan for closing ) and see an identifier token with
currently tainted identifier.
That makes sure that by the time we get past the expanded body (and
untaint the left-hand side of macro), all tokens bearing that identifier
will be seen and marked noexpand.
There is more elegant variant (it's practically straight from text of
standard - set noexpand only in dup_token() and make it
if (token_type(token) == TOKEN_IDENT)
alloc->noexpand = token->noexpand | token->ident->tainted;
which is as close as to transliteration of 6.10.3.4(2) as it gets), but
before we can go for it, we need to sort out another problem - order of
expansion/copying for arguments.
So for now here's an equivalent heavier variant with a wart ((3) above)
that works even with current expand_arguments() and when that gets sorted
out we'll be able to get anti-recursion logics absolutely straightforward.
And yes, it does preprocessor1.c correctly; it even get much subtler
preprocessor7.c right.
Diffstat (limited to 'token.h')
-rw-r--r-- | token.h | 4 |
1 files changed, 3 insertions, 1 deletions
@@ -43,6 +43,7 @@ struct ident { struct ident *next; /* Hash chain of identifiers */ struct symbol *symbols; /* Pointer to semantic meaning list */ unsigned char len; /* Length of identifier name */ + unsigned char tainted; char name[]; /* Actual identifier */ }; @@ -57,6 +58,7 @@ enum token_type { TOKEN_STREAMBEGIN, TOKEN_STREAMEND, TOKEN_MACRO_ARGUMENT, + TOKEN_UNTAINT, }; /* Combination tokens */ @@ -120,7 +122,7 @@ struct string { struct token { struct position pos; struct token *next; - struct token *parent; + int noexpand; union { char *number; struct ident *ident; |