Commit 1ce676a0 by Neil Booth Committed by Neil Booth

cpphash.h (_cpp_push_text_context): Update.

	* cpphash.h (_cpp_push_text_context): Update.
	(_cpp_arguments_ok): New.
	* cppmacro.c (_cpp_arguments_ok): New, split out from...
	(collect_args): ...here.
	(_cpp_push_text_context): Change inputs.
	* cpptrad.c (struct fun_macro, maybe_start_funlike, save_argument,
	replace_args_and_push): New.
	(lex_identifier, _cpp_lex_identifier_trad, scan_parameters):
	Don't use IS macros directly.
	(scan_out_logical_line): Handle function-like macro argument
	collection.
	(push_replacement_text): Update.
	(replacement_length): Remove.
	(_cpp_create_trad_definition): Don't skip whitespace before
	checking for '('.

From-SVN: r54412
parent 25f2e176
2002-06-09 Neil Booth <neil@daikokuya.demon.co.uk>
* cpphash.h (_cpp_push_text_context): Update.
(_cpp_arguments_ok): New.
* cppmacro.c (_cpp_arguments_ok): New, split out from...
(collect_args): ...here.
(_cpp_push_text_context): Change inputs.
* cpptrad.c (struct fun_macro, maybe_start_funlike, save_argument,
replace_args_and_push): New.
(lex_identifier, _cpp_lex_identifier_trad, scan_parameters):
Don't use IS macros directly.
(scan_out_logical_line): Handle function-like macro argument
collection.
(push_replacement_text): Update.
(replacement_length): Remove.
(_cpp_create_trad_definition): Don't skip whitespace before
checking for '('.
2002-06-09 Marek Michalkiewicz <marekm@amelek.gda.pl>
* config/avr/avr.c (avr_mcu_types): Update for new devices.
......
......@@ -438,9 +438,12 @@ extern void _cpp_free_definition PARAMS ((cpp_hashnode *));
extern bool _cpp_create_definition PARAMS ((cpp_reader *, cpp_hashnode *));
extern void _cpp_pop_context PARAMS ((cpp_reader *));
extern void _cpp_push_text_context PARAMS ((cpp_reader *, cpp_hashnode *,
const uchar *, const uchar*));
const uchar *, size_t));
extern bool _cpp_save_parameter PARAMS ((cpp_reader *, cpp_macro *,
cpp_hashnode *));
extern bool _cpp_arguments_ok PARAMS ((cpp_reader *, cpp_macro *,
const cpp_hashnode *,
unsigned int));
/* In cpphash.c */
extern void _cpp_init_hashtable PARAMS ((cpp_reader *, hash_table *));
......
......@@ -451,6 +451,52 @@ paste_all_tokens (pfile, lhs)
push_token_context (pfile, NULL, lhs, 1);
}
/* Returns TRUE if the number of arguments ARGC supplied in an
invocation of the MACRO referenced by NODE is valid. An empty
invocation to a macro with no parameters should pass ARGC as zero.
Note that MACRO cannot necessarily be deduced from NODE, in case
NODE was redefined whilst collecting arguments. */
bool
_cpp_arguments_ok (pfile, macro, node, argc)
cpp_reader *pfile;
cpp_macro *macro;
const cpp_hashnode *node;
unsigned int argc;
{
if (argc == macro->paramc)
return true;
if (argc < macro->paramc)
{
/* As an extension, a rest argument is allowed to not appear in
the invocation at all.
e.g. #define debug(format, args...) something
debug("string");
This is exactly the same as if there had been an empty rest
argument - debug("string", ). */
if (argc + 1 == macro->paramc && macro->variadic)
{
if (CPP_PEDANTIC (pfile) && ! macro->syshdr)
cpp_error (pfile, DL_PEDWARN,
"ISO C99 requires rest arguments to be used");
return true;
}
cpp_error (pfile, DL_ERROR,
"macro \"%s\" requires %u arguments, but only %u given",
NODE_NAME (node), macro->paramc, argc);
}
else
cpp_error (pfile, DL_ERROR,
"macro \"%s\" passed %u arguments, but takes just %u",
NODE_NAME (node), argc, macro->paramc);
return false;
}
/* Reads and returns the arguments to a function-like macro
invocation. Assumes the opening parenthesis has been processed.
If there is an error, emits an appropriate diagnostic and returns
......@@ -466,7 +512,6 @@ collect_args (pfile, node)
macro_arg *args, *arg;
const cpp_token *token;
unsigned int argc;
bool error = false;
macro = node->value.macro;
if (macro->paramc)
......@@ -561,47 +606,17 @@ collect_args (pfile, node)
cpp_error (pfile, DL_ERROR,
"unterminated argument list invoking macro \"%s\"",
NODE_NAME (node));
error = true;
}
else if (argc < macro->paramc)
{
/* As an extension, a rest argument is allowed to not appear in
the invocation at all.
e.g. #define debug(format, args...) something
debug("string");
This is exactly the same as if there had been an empty rest
argument - debug("string", ). */
if (argc + 1 == macro->paramc && macro->variadic)
{
if (CPP_PEDANTIC (pfile) && ! macro->syshdr)
cpp_error (pfile, DL_PEDWARN,
"ISO C99 requires rest arguments to be used");
}
else
{
cpp_error (pfile, DL_ERROR,
"macro \"%s\" requires %u arguments, but only %u given",
NODE_NAME (node), macro->paramc, argc);
error = true;
}
}
else if (argc > macro->paramc)
else
{
/* Empty argument to a macro taking no arguments is OK. */
if (argc != 1 || arg->count)
{
cpp_error (pfile, DL_ERROR,
"macro \"%s\" passed %u arguments, but takes just %u",
NODE_NAME (node), argc, macro->paramc);
error = true;
}
/* A single empty argument is counted as no argument. */
if (argc == 1 && macro->paramc == 0 && args[0].count == 0)
argc = 0;
if (_cpp_arguments_ok (pfile, macro, node, argc))
return base_buff;
}
if (!error)
return base_buff;
/* An error occurred. */
_cpp_release_buff (pfile, base_buff);
return NULL;
}
......@@ -919,10 +934,11 @@ push_token_context (pfile, macro, first, count)
/* Push a traditional macro's replacement text. */
void
_cpp_push_text_context (pfile, macro, start, end)
_cpp_push_text_context (pfile, macro, start, len)
cpp_reader *pfile;
cpp_hashnode *macro;
const uchar *start, *end;
const uchar *start;
size_t len;
{
cpp_context *context = next_context (pfile);
......@@ -930,7 +946,7 @@ _cpp_push_text_context (pfile, macro, start, end)
context->macro = macro;
context->buff = NULL;
CUR (context) = start;
RLIMIT (context) = end;
RLIMIT (context) = start + len;
}
/* Expand an argument ARG before replacing parameters in a
......
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