From eb3948d14fb48860754f84cdc8c0d507d89899fa Mon Sep 17 00:00:00 2001 From: zack Date: Thu, 10 Feb 2000 23:47:04 +0000 Subject: [PATCH] * cppexp.c: Don't include cpphash.h. (parse_charconst, cpp_lex): Use cpp_defined. (cpp_lex): Use get_directive_token throughout. Remove unnecessary cases from switch. Move assertion-handling code down to OTHER case. (cpp_parse_expr): If we see '+' or '-', check the context to determine if they are unary or binary operators. Streamline the jumps a bit. Do not call skip_rest_of_line. * cpplib.c: Make skip_rest_of_line and cpp_skip_hspace static. Export get_directive_token. Update commentary. (cpp_defined): New function. (do_define): Remove reference to T_PCSTRING. Call free_definition to release memory for old definition, when redefining a macro. (eval_if_expression): Set only_seen_white to 0 before calling cpp_parse_expr. Call skip_rest_of_line after it returns. (cpp_read_check_assertion): Don't preserve a pointer into the token buffer across a call to cpp_get_token. * Makefile.in (cppexp.o): Don't depend on cpphash.h. * cppfiles.c (redundant_include_p): Use cpp_defined. * cpphash.c (free_definition): New function. (delete_macro): Use it. Update commentary. * cpphash.h: Typedef HASHNODE here. Prototype cpp_lookup and free_definition. * cpplib.h: Don't typedef HASHNODE here. Delete T_PCSTRING from enum node_type. Prototype cpp_defined and get_directive_token. Don't prototype cpp_lookup, skip_rest_of_line, or cpp_skip_hspace. * fix-header.c (check_macro_names): Use cpp_defined. (read_scan_file): Set inhibit_warnings and inhibit_errors in the options structure. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@31908 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/ChangeLog | 36 +++++++++++++ gcc/Makefile.in | 2 +- gcc/cppexp.c | 111 +++++++++++++++----------------------- gcc/cppfiles.c | 2 +- gcc/cpphash.c | 41 +++++++------- gcc/cpphash.h | 3 ++ gcc/cpplib.c | 65 +++++++++++++--------- gcc/cpplib.h | 11 ++-- gcc/fix-header.c | 6 ++- gcc/testsuite/gcc.dg/20000207-1.c | 16 ++++++ gcc/testsuite/gcc.dg/20000207-2.c | 16 ++++++ 11 files changed, 184 insertions(+), 125 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/20000207-1.c create mode 100644 gcc/testsuite/gcc.dg/20000207-2.c diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 5eff6b0..255ab22 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,39 @@ +2000-02-10 Zack Weinberg + + * cppexp.c: Don't include cpphash.h. + (parse_charconst, cpp_lex): Use cpp_defined. + (cpp_lex): Use get_directive_token throughout. Remove + unnecessary cases from switch. Move assertion-handling code + down to OTHER case. + (cpp_parse_expr): If we see '+' or '-', check the context to + determine if they are unary or binary operators. Streamline + the jumps a bit. Do not call skip_rest_of_line. + + * cpplib.c: Make skip_rest_of_line and cpp_skip_hspace + static. Export get_directive_token. Update commentary. + (cpp_defined): New function. + (do_define): Remove reference to T_PCSTRING. Call + free_definition to release memory for old definition, when + redefining a macro. + (eval_if_expression): Set only_seen_white to 0 before calling + cpp_parse_expr. Call skip_rest_of_line after it returns. + (cpp_read_check_assertion): Don't preserve a pointer into the + token buffer across a call to cpp_get_token. + + * Makefile.in (cppexp.o): Don't depend on cpphash.h. + * cppfiles.c (redundant_include_p): Use cpp_defined. + * cpphash.c (free_definition): New function. + (delete_macro): Use it. Update commentary. + * cpphash.h: Typedef HASHNODE here. Prototype cpp_lookup and + free_definition. + * cpplib.h: Don't typedef HASHNODE here. Delete T_PCSTRING + from enum node_type. Prototype cpp_defined and get_directive_token. + Don't prototype cpp_lookup, skip_rest_of_line, or cpp_skip_hspace. + + * fix-header.c (check_macro_names): Use cpp_defined. + (read_scan_file): Set inhibit_warnings and inhibit_errors in + the options structure. + 2000-02-10 Franz Sirl * c-pragma.c (maximum_field_alignment): Remove duplicate declaration. diff --git a/gcc/Makefile.in b/gcc/Makefile.in index f231557..31a0173 100644 --- a/gcc/Makefile.in +++ b/gcc/Makefile.in @@ -2043,7 +2043,7 @@ cpplib.o: cpplib.c $(CONFIG_H) cpplib.h intl.h system.h cpphash.h cpphash.o: cpphash.c $(CONFIG_H) cpplib.h intl.h system.h cpphash.h cppalloc.o: cppalloc.c $(CONFIG_H) cpplib.h intl.h system.h cpperror.o: cpperror.c $(CONFIG_H) cpplib.h intl.h system.h -cppexp.o: cppexp.c $(CONFIG_H) cpplib.h intl.h system.h cpphash.h +cppexp.o: cppexp.c $(CONFIG_H) cpplib.h intl.h system.h cppfiles.o: cppfiles.c $(CONFIG_H) cpplib.h intl.h system.h cppinit.o: cppinit.c $(CONFIG_H) cpplib.h intl.h system.h \ diff --git a/gcc/cppexp.c b/gcc/cppexp.c index 7f8c917..a7db2ce 100644 --- a/gcc/cppexp.c +++ b/gcc/cppexp.c @@ -27,7 +27,6 @@ Written by Per Bothner 1994. */ #include "config.h" #include "system.h" #include "cpplib.h" -#include "cpphash.h" #ifdef MULTIBYTE_CHARS #include @@ -331,8 +330,8 @@ parse_charconst (pfile, start, end) /* If char type is signed, sign-extend the constant. */ num_bits = num_chars * width; - if (cpp_lookup (pfile, (const U_CHAR *)"__CHAR_UNSIGNED__", - sizeof ("__CHAR_UNSIGNED__")-1) + if (cpp_defined (pfile, (const U_CHAR *)"__CHAR_UNSIGNED__", + sizeof ("__CHAR_UNSIGNED__")-1) || ((result >> (num_bits - 1)) & 1) == 0) op.value = result & ((unsigned HOST_WIDEST_INT) ~0 >> (HOST_BITS_PER_WIDEST_INT - num_bits)); @@ -377,56 +376,28 @@ cpp_lex (pfile, skip_evaluation) cpp_reader *pfile; int skip_evaluation; { - U_CHAR c; struct token *toktab; enum cpp_token token; struct operation op; U_CHAR *tok_start, *tok_end; - int old_written; - - retry: + long old_written; old_written = CPP_WRITTEN (pfile); - cpp_skip_hspace (pfile); - c = CPP_BUF_PEEK (CPP_BUFFER (pfile)); - if (c == '#') - { - op.op = INT; - op.value = cpp_read_check_assertion (pfile); - return op; - } - - if (c == '\n') - { - op.op = 0; - return op; - } + token = get_directive_token (pfile); - token = cpp_get_token (pfile); tok_start = pfile->token_buffer + old_written; tok_end = CPP_PWRITTEN (pfile); - pfile->limit = tok_start; + CPP_SET_WRITTEN (pfile, old_written); switch (token) { case CPP_EOF: /* Should not happen ... */ case CPP_VSPACE: op.op = 0; return op; - case CPP_POP: - if (CPP_BUFFER (pfile)->fname != NULL) - { - op.op = 0; - return op; - } - cpp_pop_buffer (pfile); - goto retry; - case CPP_HSPACE: - case CPP_COMMENT: - goto retry; case CPP_NUMBER: return parse_number (pfile, tok_start, tok_end); case CPP_STRING: - cpp_error (pfile, "string constants not allowed in #if expressions"); + cpp_error (pfile, "string constants are not allowed in #if expressions"); op.op = ERROR; return op; case CPP_CHAR: @@ -445,45 +416,38 @@ cpp_lex (pfile, skip_evaluation) else { int paren = 0, len; - cpp_buffer *ip = CPP_BUFFER (pfile); U_CHAR *tok; - HASHNODE *hp; - cpp_skip_hspace (pfile); - if (*ip->cur == '(') + pfile->no_macro_expand++; + token = get_directive_token (pfile); + if (token == CPP_LPAREN) { paren++; - ip->cur++; /* Skip over the paren */ - cpp_skip_hspace (pfile); + CPP_SET_WRITTEN (pfile, old_written); + token = get_directive_token (pfile); } - if (!is_idstart(*ip->cur)) - goto oops; - if (ip->cur[0] == 'L' && (ip->cur[1] == '\'' || ip->cur[1] == '"')) + if (token != CPP_NAME) goto oops; - tok = ip->cur; - while (is_idchar(*ip->cur)) - ++ip->cur; - len = ip->cur - tok; - cpp_skip_hspace (pfile); + + tok = pfile->token_buffer + old_written; + len = CPP_PWRITTEN (pfile) - tok; + if (cpp_defined (pfile, tok, len)) + op.value = 1; + if (paren) { - if (*ip->cur != ')') + if (get_directive_token (pfile) != CPP_RPAREN) goto oops; - ++ip->cur; - } - hp = cpp_lookup (pfile, tok, len); - if (hp != NULL) - { - if (hp->type == T_POISON) - cpp_error (pfile, "attempt to use poisoned `%s'", hp->name); - else - op.value = 1; } + CPP_SET_WRITTEN (pfile, old_written); + pfile->no_macro_expand--; } return op; oops: + CPP_SET_WRITTEN (pfile, old_written); + pfile->no_macro_expand--; cpp_error (pfile, "`defined' without an identifier"); return op; @@ -501,6 +465,13 @@ cpp_lex (pfile, skip_evaluation) op.op = toktab->token; return op; } + else if (tok_start + 1 == tok_end && *tok_start == '#') + { + CPP_FORWARD (CPP_BUFFER (pfile), -1); + op.op = INT; + op.value = cpp_read_check_assertion (pfile); + return op; + } /* fall through */ default: op.op = *tok_start; @@ -736,15 +707,16 @@ cpp_parse_expr (pfile) cpp_ice (pfile, "cpp_lex returns a NAME"); goto syntax_error; case INT: case CHAR: - top->value = op.value; - top->unsignedp = op.unsignedp; goto set_value; case 0: lprio = 0; goto maybe_reduce; case '+': case '-': - /* Is this correct if unary ? FIXME */ - flags = RIGHT_OPERAND_REQUIRED; - lprio = PLUS_PRIO; rprio = lprio + 1; goto maybe_reduce; + if (top->flags & HAVE_VALUE) + { + lprio = PLUS_PRIO; + goto binop; + } + /* else fall through */ case '!': case '~': flags = RIGHT_OPERAND_REQUIRED; rprio = UNARY_PRIO; lprio = rprio + 1; goto maybe_reduce; @@ -777,10 +749,6 @@ cpp_parse_expr (pfile) goto maybe_reduce; case ERROR: goto syntax_error; - binop: - flags = LEFT_OPERAND_REQUIRED|RIGHT_OPERAND_REQUIRED; - rprio = lprio + 1; - goto maybe_reduce; default: cpp_error (pfile, "invalid character in #if"); goto syntax_error; @@ -793,9 +761,15 @@ cpp_parse_expr (pfile) cpp_error (pfile, "syntax error in #if"); goto syntax_error; } + top->value = op.value; + top->unsignedp = op.unsignedp; top->flags |= HAVE_VALUE; continue; + binop: + flags = LEFT_OPERAND_REQUIRED|RIGHT_OPERAND_REQUIRED; + rprio = lprio + 1; + maybe_reduce: /* Push an operator, and check if we can reduce now. */ while (top->rprio > lprio) @@ -1065,6 +1039,5 @@ cpp_parse_expr (pfile) syntax_error: if (stack != init_stack) free (stack); - skip_rest_of_line (pfile); return 0; } diff --git a/gcc/cppfiles.c b/gcc/cppfiles.c index deb8bf0..a00fb89 100644 --- a/gcc/cppfiles.c +++ b/gcc/cppfiles.c @@ -286,7 +286,7 @@ redundant_include_p (pfile, ihash, ilist) included again if the string is the name of a defined macro. */ return (i->control_macro && (i->control_macro[0] == '\0' - || cpp_lookup (pfile, i->control_macro, -1))) + || cpp_defined (pfile, i->control_macro, -1))) ? (struct include_hash *)-1 : i; return 0; diff --git a/gcc/cpphash.c b/gcc/cpphash.c index 0a4e860..7b0bea2 100644 --- a/gcc/cpphash.c +++ b/gcc/cpphash.c @@ -140,20 +140,31 @@ cpp_lookup (pfile, name, len) return (HASHNODE *) 0; } +/* Free a DEFINITION structure. Used by delete_macro, and by + do_define when redefining macros. */ + +void +free_definition (d) + DEFINITION *d; +{ + struct reflist *ap, *nextap; + + for (ap = d->pattern; ap != NULL; ap = nextap) + { + nextap = ap->next; + free (ap); + } + if (d->nargs >= 0) + free (d->argnames); + free (d); +} + /* * Delete a hash node. Some weirdness to free junk from macros. * More such weirdness will have to be added if you define more hash * types that need it. */ -/* Note that the DEFINITION of a macro is removed from the hash table - but its storage is not freed. This would be a storage leak - except that it is not reasonable to keep undefining and redefining - large numbers of macros many times. - In any case, this is necessary, because a macro can be #undef'd - in the middle of reading the arguments to a call to it. - If #undef freed the DEFINITION, that would crash. */ - void delete_macro (hp) HASHNODE *hp; @@ -170,19 +181,7 @@ delete_macro (hp) *hp->bucket_hdr = hp->next; if (hp->type == T_MACRO) - { - DEFINITION *d = hp->value.defn; - struct reflist *ap, *nextap; - - for (ap = d->pattern; ap != NULL; ap = nextap) - { - nextap = ap->next; - free (ap); - } - if (d->nargs >= 0) - free (d->argnames); - free (d); - } + free_definition (hp->value.defn); free (hp); } diff --git a/gcc/cpphash.h b/gcc/cpphash.h index 960700c..b974284 100644 --- a/gcc/cpphash.h +++ b/gcc/cpphash.h @@ -83,6 +83,7 @@ union hashval struct hashnode *aschain; /* #assert */ }; +typedef struct hashnode HASHNODE; struct hashnode { struct hashnode *next; /* double links for easy deletion */ struct hashnode *prev; @@ -97,6 +98,8 @@ struct hashnode { extern HASHNODE *cpp_install PARAMS ((cpp_reader *, const U_CHAR *, int, enum node_type, const char *)); +extern HASHNODE *cpp_lookup PARAMS ((cpp_reader *, const U_CHAR *, int)); +extern void free_definition PARAMS ((DEFINITION *)); extern void delete_macro PARAMS ((HASHNODE *)); extern MACRODEF create_definition PARAMS ((U_CHAR *, U_CHAR *, diff --git a/gcc/cpplib.c b/gcc/cpplib.c index 896d602..c64e682 100644 --- a/gcc/cpplib.c +++ b/gcc/cpplib.c @@ -93,11 +93,12 @@ static int null_cleanup PARAMS ((cpp_buffer *, cpp_reader *)); static int skip_comment PARAMS ((cpp_reader *, int)); static int copy_comment PARAMS ((cpp_reader *, int)); static void copy_rest_of_line PARAMS ((cpp_reader *)); +static void skip_rest_of_line PARAMS ((cpp_reader *)); +static void cpp_skip_hspace PARAMS ((cpp_reader *)); static int handle_directive PARAMS ((cpp_reader *)); static void pass_thru_directive PARAMS ((const U_CHAR *, size_t, cpp_reader *, const struct directive *)); -static enum cpp_token get_directive_token PARAMS ((cpp_reader *)); static int read_line_number PARAMS ((cpp_reader *, int *)); static U_CHAR *detect_if_not_defined PARAMS ((cpp_reader *)); static int consider_directive_while_skipping PARAMS ((cpp_reader *, @@ -192,12 +193,7 @@ cpp_grow_buffer (pfile, n) CPP_SET_WRITTEN (pfile, old_written); } -/* Process the string STR as if it appeared as the body of a #define - If STR is just an identifier, define it with value 1. - If STR has anything after the identifier, then it should - be identifier=definition. */ - -/* Process the string STR as if it appeared as the body of a #define +/* Process the string STR as if it appeared as the body of a #define. If STR is just an identifier, define it with value 1. If STR has anything after the identifier, then it should be identifier=definition. */ @@ -252,6 +248,21 @@ cpp_assert (pfile, str) } } +/* Determine whether the identifier ID, of length LEN, is a defined macro. */ +int +cpp_defined (pfile, id, len) + cpp_reader *pfile; + const U_CHAR *id; + int len; +{ + HASHNODE *hp = cpp_lookup (pfile, id, len); + if (hp && hp->type == T_POISON) + { + cpp_error (pfile, "attempt to use poisoned `%s'", hp->name); + return 0; + } + return (hp != NULL); +} static enum cpp_token null_underflow (pfile) @@ -407,7 +418,7 @@ copy_comment (pfile, m) /* Skip whitespace \-newline and comments. Does not macro-expand. */ -void +static void cpp_skip_hspace (pfile) cpp_reader *pfile; { @@ -508,7 +519,7 @@ copy_rest_of_line (pfile) the scan itself. >75% of calls to copy_r_o_l are from here or skip_if_group, which means the common case is to copy stuff into the token_buffer only to discard it. */ -void +static void skip_rest_of_line (pfile) cpp_reader *pfile; { @@ -684,11 +695,8 @@ do_define (pfile, keyword) if ((hp = cpp_lookup (pfile, mdef.symnam, mdef.symlen)) != NULL) { int ok = 0; - /* Redefining a precompiled key is ok. */ - if (hp->type == T_PCSTRING) - ok = 1; /* Redefining a poisoned identifier is even worse than `not ok'. */ - else if (hp->type == T_POISON) + if (hp->type == T_POISON) ok = -1; /* Redefining a macro is ok if the definitions are the same. */ else if (hp->type == T_MACRO) @@ -713,6 +721,7 @@ do_define (pfile, keyword) { /* Replace the old definition. */ hp->type = new_type; + free_definition (hp->value.defn); hp->value.defn = mdef.defn; } } @@ -986,7 +995,7 @@ output_line_command (pfile, file_change) /* Like cpp_get_token, except that it does not read past end-of-line. Also, horizontal space is skipped, and macros are popped. */ -static enum cpp_token +enum cpp_token get_directive_token (pfile) cpp_reader *pfile; { @@ -1872,8 +1881,13 @@ eval_if_expression (pfile) HOST_WIDEST_INT value; long old_written = CPP_WRITTEN (pfile); + /* Work around bug in cpp_get_token where it may mistake an + assertion for a directive. */ + pfile->only_seen_white = 0; + value = cpp_parse_expr (pfile); + skip_rest_of_line (pfile); CPP_SET_WRITTEN (pfile, old_written); /* Pop */ return value; @@ -2631,10 +2645,7 @@ cpp_get_token (pfile) return CPP_NAME; } - /* If macro wants an arglist, verify that a '(' follows. - first skip all whitespace, copying it to the output - after the macro name. Then, if there is no '(', - decide this is not a macro call and leave things that way. */ + /* If macro wants an arglist, verify that a '(' follows. */ if (hp->type == T_MACRO && hp->value.defn->nargs >= 0) { int macbuf_whitespace = 0; @@ -3130,9 +3141,9 @@ int cpp_read_check_assertion (pfile) cpp_reader *pfile; { - U_CHAR *name = CPP_PWRITTEN (pfile); + U_CHAR *name; int result; - HASHNODE *hp; + long written = CPP_WRITTEN (pfile); FORWARD (1); /* Skip '#' */ cpp_skip_hspace (pfile); @@ -3140,15 +3151,21 @@ cpp_read_check_assertion (pfile) result = 0; else { - hp = cpp_lookup (pfile, name, CPP_PWRITTEN (pfile) - name); - result = (hp != 0); + name = pfile->token_buffer + written; + result = cpp_defined (pfile, name, CPP_PWRITTEN (pfile) - name); } - pfile->limit = name; + CPP_SET_WRITTEN (pfile, written); return result; } -/* Remember the current position of PFILE. */ +/* Remember the current position of PFILE so it may be returned to + after looking ahead a bit. + + Note that when you set a mark, you _must_ return to that mark. You + may not forget about it and continue parsing. You may not pop a + buffer with an active mark. You may not call CPP_BUMP_LINE while a + mark is active. */ static void parse_set_mark (pfile) diff --git a/gcc/cpplib.h b/gcc/cpplib.h index 266b903..82eb55c 100644 --- a/gcc/cpplib.h +++ b/gcc/cpplib.h @@ -61,8 +61,8 @@ typedef int (*parse_cleanup_t) PARAMS((cpp_buffer *, cpp_reader *)); extern int cpp_handle_option PARAMS ((cpp_reader *, int, char **)); extern int cpp_handle_options PARAMS ((cpp_reader *, int, char **)); extern enum cpp_token cpp_get_token PARAMS ((cpp_reader *)); -extern void cpp_skip_hspace PARAMS((cpp_reader *)); extern enum cpp_token cpp_get_non_space_token PARAMS ((cpp_reader *)); +extern enum cpp_token get_directive_token PARAMS ((cpp_reader *)); /* This frees resources used by PFILE. */ extern void cpp_cleanup PARAMS ((cpp_reader *PFILE)); @@ -139,9 +139,6 @@ struct file_name_map_list; Applying cpp_get_token repeatedly yields a stream of pre-processor tokens. Usually, there is only one cpp_reader object active. */ -struct hashnode; -typedef struct hashnode HASHNODE; - struct cpp_reader { parse_underflow_t get_token; @@ -169,7 +166,7 @@ struct cpp_reader /* Hash table of macros and assertions. See cpphash.c */ #define HASHSIZE 1403 - HASHNODE **hashtab; + struct hashnode **hashtab; /* Hash table of other included files. See cppfiles.c */ #define ALL_INCLUDE_HASHSIZE 71 @@ -600,7 +597,6 @@ enum node_type { T_CONST, /* Constant string, used by `__SIZE_TYPE__' etc */ T_MACRO, /* macro defined by `#define' */ T_DISABLED, /* macro temporarily turned off for rescan */ - T_PCSTRING, /* precompiled string (hashval is KEYDEF *) */ T_POISON, /* defined with `#pragma poison' */ T_UNUSED /* Used for something not defined. */ }; @@ -686,13 +682,12 @@ extern void cpp_grow_buffer PARAMS ((cpp_reader *, long)); extern cpp_buffer *cpp_push_buffer PARAMS ((cpp_reader *, unsigned char *, long)); extern cpp_buffer *cpp_pop_buffer PARAMS ((cpp_reader *)); -extern HASHNODE *cpp_lookup PARAMS ((cpp_reader *, const U_CHAR *, int)); +extern int cpp_defined PARAMS ((cpp_reader *, const U_CHAR *, int)); extern void cpp_reader_init PARAMS ((cpp_reader *)); extern void cpp_options_init PARAMS ((cpp_options *)); extern int cpp_start_read PARAMS ((cpp_reader *, char *)); extern int cpp_read_check_assertion PARAMS ((cpp_reader *)); -extern void skip_rest_of_line PARAMS ((cpp_reader *)); extern void cpp_finish PARAMS ((cpp_reader *)); extern void quote_string PARAMS ((cpp_reader *, const char *)); diff --git a/gcc/fix-header.c b/gcc/fix-header.c index 802d636..6b1c56f 100644 --- a/gcc/fix-header.c +++ b/gcc/fix-header.c @@ -603,7 +603,7 @@ check_macro_names (pfile, names) { while (*names) { - if (cpp_lookup (pfile, names, -1)) + if (cpp_defined (pfile, names, -1)) recognized_macro (names); names += strlen (names) + 1; } @@ -626,6 +626,10 @@ read_scan_file (in_fname, argc, argv) cpp_reader_init (&scan_in); scan_in.opts = &scan_options; cpp_options_init (&scan_options); + /* We are going to be scanning a header file out of its proper context, + so ignore warnings and errors. */ + scan_options.inhibit_warnings = 1; + scan_options.inhibit_errors = 1; i = cpp_handle_options (&scan_in, argc, argv); if (i < argc && ! CPP_FATAL_ERRORS (&scan_in)) cpp_fatal (&scan_in, "Invalid option `%s'", argv[i]); diff --git a/gcc/testsuite/gcc.dg/20000207-1.c b/gcc/testsuite/gcc.dg/20000207-1.c new file mode 100644 index 0000000..931cc0d --- /dev/null +++ b/gcc/testsuite/gcc.dg/20000207-1.c @@ -0,0 +1,16 @@ +/* { dg-do preprocess } */ + +/* Test for proper handling of unary minus in #if. */ + +#if !(-1) +#error Error /* { dg-bogus "Error" "case !(-1)" } */ +#endif + +#if !-1 +#error Error /* { dg-bogus "Error" "case !-1" } */ +#endif + +#if -1 +#else +#error Error /* { dg-bogus "Error" "case -1" } */ +#endif diff --git a/gcc/testsuite/gcc.dg/20000207-2.c b/gcc/testsuite/gcc.dg/20000207-2.c new file mode 100644 index 0000000..fbdf39e --- /dev/null +++ b/gcc/testsuite/gcc.dg/20000207-2.c @@ -0,0 +1,16 @@ +/* { dg-do preprocess } */ + +/* Test for proper handling of unary plus in #if. */ + +#if !(+1) +#error Error /* { dg-bogus "Error" "case !(+1)" } */ +#endif + +#if !+1 +#error Error /* { dg-bogus "Error" "case !+1" } */ +#endif + +#if +1 +#else +#error Error /* { dg-bogus "Error" "case +1" } */ +#endif -- 2.7.4