Commit a94c1199 by Neil Booth Committed by Neil Booth

cpplex.c (parse_args): Don't set VOID_REST flag.

        * cpplex.c (parse_args): Don't set VOID_REST flag.
	(Fix diagnostic merge problem).
        (CONTEXT_VARARGS): New flag.
        (maybe_paste_with_next): Set context earlier in loop.  Use
        it.  Do varargs test with CONTEXT_VARARGS flag.
        (push_arg_context): Set CONTEXT_VARARGS flag if we're
        pushing an argument context for a varargs argument.
        * cpplib.h (VOID_REST): Delete.
        * gcc.dg/cpp/vararg1.c: Add test case.

From-SVN: r36638
parent 15e2ab71
Tue 26-Sep-2000 00:16:22 BST Neil Booth <neilb@earthling.net>
* cpplex.c (parse_args): Don't set VOID_REST flag.
(CONTEXT_VARARGS): New flag.
(maybe_paste_with_next): Set context earlier in loop. Use
it. Do varargs test with CONTEXT_VARARGS flag.
(push_arg_context): Set CONTEXT_VARARGS flag if we're
pushing an argument context for a varargs argument.
* cpplib.h (VOID_REST): Delete.
* gcc.dg/cpp/vararg1.c: Add test case.
2000-09-25 Branko Cibej <branko.cibej@hermes.si> 2000-09-25 Branko Cibej <branko.cibej@hermes.si>
* flags.h: Declare warning flag warn_system_headers. * flags.h: Declare warning flag warn_system_headers.
......
...@@ -52,6 +52,7 @@ static const cpp_token eof_token = {0, 0, CPP_EOF, 0 UNION_INIT_ZERO}; ...@@ -52,6 +52,7 @@ static const cpp_token eof_token = {0, 0, CPP_EOF, 0 UNION_INIT_ZERO};
#define CONTEXT_PASTER (1 << 1) /* An argument context on RHS of ##. */ #define CONTEXT_PASTER (1 << 1) /* An argument context on RHS of ##. */
#define CONTEXT_RAW (1 << 2) /* If argument tokens already expanded. */ #define CONTEXT_RAW (1 << 2) /* If argument tokens already expanded. */
#define CONTEXT_ARG (1 << 3) /* If an argument context. */ #define CONTEXT_ARG (1 << 3) /* If an argument context. */
#define CONTEXT_VARARGS (1 << 4) /* If a varargs argument context. */
typedef struct cpp_context cpp_context; typedef struct cpp_context cpp_context;
struct cpp_context struct cpp_context
...@@ -1209,24 +1210,9 @@ lex_token (pfile, result) ...@@ -1209,24 +1210,9 @@ lex_token (pfile, result)
irrespective of conformance mode, because lots of irrespective of conformance mode, because lots of
broken systems do that and trying to clean it up in broken systems do that and trying to clean it up in
fixincludes is a nightmare. */ fixincludes is a nightmare. */
if (CPP_OPTION (pfile, cplusplus_comments) if (CPP_OPTION (pfile, c89) && CPP_PEDANTIC (pfile)
|| CPP_IN_SYSTEM_HEADER (pfile)) && ! buffer->warned_cplusplus_comments)
{ {
if (CPP_OPTION (pfile, c89) && CPP_PEDANTIC (pfile)
&& ! buffer->warned_cplusplus_comments)
{
cpp_pedwarn (pfile,
"C++ style comments are not allowed in ISO C89");
cpp_pedwarn (pfile,
"(this will be reported only once per input file)");
buffer->warned_cplusplus_comments = 1;
}
comment_start = buffer->cur;
/* Skip_line_comment updates buffer->read_ahead. */
if (skip_line_comment (pfile))
cpp_warning_with_line (pfile, result->line, result->col,
"multi-line comment");
cpp_pedwarn (pfile, cpp_pedwarn (pfile,
"C++ style comments are not allowed in ISO C89"); "C++ style comments are not allowed in ISO C89");
cpp_pedwarn (pfile, cpp_pedwarn (pfile,
...@@ -1234,6 +1220,7 @@ lex_token (pfile, result) ...@@ -1234,6 +1220,7 @@ lex_token (pfile, result)
buffer->warned_cplusplus_comments = 1; buffer->warned_cplusplus_comments = 1;
} }
/* Skip_line_comment updates buffer->read_ahead. */
if (skip_line_comment (pfile)) if (skip_line_comment (pfile))
cpp_warning_with_line (pfile, result->line, result->col, cpp_warning_with_line (pfile, result->line, result->col,
"multi-line comment"); "multi-line comment");
...@@ -2004,9 +1991,7 @@ parse_args (pfile, hp, args) ...@@ -2004,9 +1991,7 @@ parse_args (pfile, hp, args)
{ {
/* Duplicate the placemarker. Then we can set its flags and /* Duplicate the placemarker. Then we can set its flags and
position and safely be using more than one. */ position and safely be using more than one. */
cpp_token *pm = duplicate_token (pfile, &placemarker_token); save_token (args, duplicate_token (pfile, &placemarker_token));
pm->flags = VOID_REST;
save_token (args, pm);
args->ends[argc] = total + 1; args->ends[argc] = total + 1;
if (CPP_OPTION (pfile, c99) && CPP_PEDANTIC (pfile)) if (CPP_OPTION (pfile, c99) && CPP_PEDANTIC (pfile))
...@@ -2316,6 +2301,7 @@ maybe_paste_with_next (pfile, token) ...@@ -2316,6 +2301,7 @@ maybe_paste_with_next (pfile, token)
pfile->paste_level = pfile->cur_context; pfile->paste_level = pfile->cur_context;
second = _cpp_get_token (pfile); second = _cpp_get_token (pfile);
pfile->paste_level = 0; pfile->paste_level = 0;
context = CURRENT_CONTEXT (pfile);
/* Ignore placemarker argument tokens (cannot be from an empty /* Ignore placemarker argument tokens (cannot be from an empty
macro since macros are not expanded). */ macro since macros are not expanded). */
...@@ -2327,7 +2313,7 @@ maybe_paste_with_next (pfile, token) ...@@ -2327,7 +2313,7 @@ maybe_paste_with_next (pfile, token)
a varargs parameter: the comma disappears if b was given a varargs parameter: the comma disappears if b was given
no actual arguments (not merely if b is an empty no actual arguments (not merely if b is an empty
argument). */ argument). */
if (token->type == CPP_COMMA && second->flags & VOID_REST) if (token->type == CPP_COMMA && (context->flags & CONTEXT_VARARGS))
pasted = duplicate_token (pfile, second); pasted = duplicate_token (pfile, second);
else else
pasted = duplicate_token (pfile, token); pasted = duplicate_token (pfile, token);
...@@ -2345,9 +2331,8 @@ maybe_paste_with_next (pfile, token) ...@@ -2345,9 +2331,8 @@ maybe_paste_with_next (pfile, token)
<whatever> came from a variable argument, because <whatever> came from a variable argument, because
the author probably intended the ## to trigger the author probably intended the ## to trigger
the special extended semantics (see above). */ the special extended semantics (see above). */
if (token->type == CPP_COMMA if (token->type == CPP_COMMA && IS_ARG_CONTEXT (context)
&& IS_ARG_CONTEXT (CURRENT_CONTEXT (pfile)) && ON_REST_ARG (context - 1))
&& ON_REST_ARG (CURRENT_CONTEXT (pfile) - 1))
/* no warning */; /* no warning */;
else else
cpp_warning (pfile, cpp_warning (pfile,
...@@ -2411,7 +2396,6 @@ maybe_paste_with_next (pfile, token) ...@@ -2411,7 +2396,6 @@ maybe_paste_with_next (pfile, token)
/* See if there is another token to be pasted onto the one we just /* See if there is another token to be pasted onto the one we just
constructed. */ constructed. */
token = pasted; token = pasted;
context = CURRENT_CONTEXT (pfile);
/* and loop */ /* and loop */
} }
return token; return token;
...@@ -2592,6 +2576,9 @@ push_arg_context (pfile, token) ...@@ -2592,6 +2576,9 @@ push_arg_context (pfile, token)
context->posn = 0; context->posn = 0;
context->level = args->level; context->level = args->level;
context->flags = CONTEXT_ARG | CONTEXT_RAW; context->flags = CONTEXT_ARG | CONTEXT_RAW;
if ((context[-1].u.list->flags & VAR_ARGS)
&& token->val.aux + 1 == (unsigned) context[-1].u.list->paramc)
context->flags |= CONTEXT_VARARGS;
context->pushed_token = 0; context->pushed_token = 0;
/* Set the flags of the first token. There is one. */ /* Set the flags of the first token. There is one. */
......
...@@ -160,7 +160,6 @@ struct cpp_string ...@@ -160,7 +160,6 @@ struct cpp_string
#define PASTE_LEFT (1 << 4) /* If on LHS of a ## operator. */ #define PASTE_LEFT (1 << 4) /* If on LHS of a ## operator. */
#define PASTED (1 << 5) /* The result of a ## operator. */ #define PASTED (1 << 5) /* The result of a ## operator. */
#define NAMED_OP (1 << 6) /* C++ named operators, also "defined". */ #define NAMED_OP (1 << 6) /* C++ named operators, also "defined". */
#define VOID_REST (1 << 7) /* When a rest arg gets zero actual args. */
/* A preprocessing token. This has been carefully packed and should /* A preprocessing token. This has been carefully packed and should
occupy 16 bytes on 32-bit hosts and 24 bytes on 64-bit hosts. */ occupy 16 bytes on 32-bit hosts and 24 bytes on 64-bit hosts. */
......
/* { dg-do run } */
/* { dg-options -w } */
/* count() used to give 1 owing to a buggy test for varargs. */
#define count(y...) count1 ( , ##y)
#define count1(y...) count2 (y,1,0)
#define count2(_,x0,n,y...) n
#if count() != 0 || count(A) != 1
#error Incorrect vararg argument counts
#endif
/* Test for changed behavior of the GNU varargs extension. /* Test for changed behavior of the GNU varargs extension.
##args, where args is a rest argument which received zero tokens, ##args, where args is a rest argument which received zero tokens,
used to delete the previous sequence of nonwhitespace characters. used to delete the previous sequence of nonwhitespace characters.
Now it deletes the previous token. */ Now it deletes the previous token. */
/* { dg-do run } */
/* { dg-options -w } */
#include <string.h> #include <string.h>
#define S(str, args...) " " str "\n", ##args #define S(str, args...) " " str "\n", ##args
...@@ -16,4 +24,3 @@ main() ...@@ -16,4 +24,3 @@ main()
const char *s = S("foo"); const char *s = S("foo");
return strchr (s, '\n') == NULL; return strchr (s, '\n') == NULL;
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment