OSDN Git Service

1999-10-15 11:16 -0700 Zack Weinberg <zack@bitmover.com>
[pf3gnuchains/gcc-fork.git] / gcc / cppexp.c
1 /* Parse C expressions for CCCP.
2    Copyright (C) 1987, 92, 94, 95, 97, 98, 1999 Free Software Foundation.
3
4 This program is free software; you can redistribute it and/or modify it
5 under the terms of the GNU General Public License as published by the
6 Free Software Foundation; either version 2, or (at your option) any
7 later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, 59 Temple Place - Suite 330,
17 Boston, MA 02111-1307, USA.
18
19  In other words, you are welcome to use, share and improve this program.
20  You are forbidden to forbid anyone else to use, share and improve
21  what you give them.   Help stamp out software-hoarding!
22
23 Written by Per Bothner 1994.  */
24
25 /* Parse a C expression from text in a string  */
26    
27 #include "config.h"
28 #include "system.h"
29 #include "cpplib.h"
30 #include "cpphash.h"
31
32 #ifdef MULTIBYTE_CHARS
33 #include <locale.h>
34 #endif
35
36 #ifndef CHAR_TYPE_SIZE
37 #define CHAR_TYPE_SIZE BITS_PER_UNIT
38 #endif
39
40 #ifndef INT_TYPE_SIZE
41 #define INT_TYPE_SIZE BITS_PER_WORD
42 #endif
43
44 #ifndef LONG_TYPE_SIZE
45 #define LONG_TYPE_SIZE BITS_PER_WORD
46 #endif
47
48 #ifndef WCHAR_TYPE_SIZE
49 #define WCHAR_TYPE_SIZE INT_TYPE_SIZE
50 #endif
51
52 #ifndef MAX_CHAR_TYPE_SIZE
53 #define MAX_CHAR_TYPE_SIZE CHAR_TYPE_SIZE
54 #endif
55
56 #ifndef MAX_INT_TYPE_SIZE
57 #define MAX_INT_TYPE_SIZE INT_TYPE_SIZE
58 #endif
59
60 #ifndef MAX_LONG_TYPE_SIZE
61 #define MAX_LONG_TYPE_SIZE LONG_TYPE_SIZE
62 #endif
63
64 #ifndef MAX_WCHAR_TYPE_SIZE
65 #define MAX_WCHAR_TYPE_SIZE WCHAR_TYPE_SIZE
66 #endif
67
68 #define MAX_CHAR_TYPE_MASK (MAX_CHAR_TYPE_SIZE < HOST_BITS_PER_WIDEST_INT \
69                             ? (~ (~ (HOST_WIDEST_INT) 0 << MAX_CHAR_TYPE_SIZE)) \
70                             : ~ (HOST_WIDEST_INT) 0)
71
72 #define MAX_WCHAR_TYPE_MASK (MAX_WCHAR_TYPE_SIZE < HOST_BITS_PER_WIDEST_INT \
73                              ? ~ (~ (HOST_WIDEST_INT) 0 << MAX_WCHAR_TYPE_SIZE) \
74                              : ~ (HOST_WIDEST_INT) 0)
75
76 /* Yield nonzero if adding two numbers with A's and B's signs can yield a
77    number with SUM's sign, where A, B, and SUM are all C integers.  */
78 #define possible_sum_sign(a, b, sum) ((((a) ^ (b)) | ~ ((a) ^ (sum))) < 0)
79
80 static void integer_overflow PARAMS ((cpp_reader *));
81 static HOST_WIDEST_INT left_shift PARAMS ((cpp_reader *, HOST_WIDEST_INT, int, unsigned HOST_WIDEST_INT));
82 static HOST_WIDEST_INT right_shift PARAMS ((cpp_reader *, HOST_WIDEST_INT, int, unsigned HOST_WIDEST_INT));
83 static struct operation parse_number PARAMS ((cpp_reader *, U_CHAR *, U_CHAR *));
84 static struct operation parse_charconst PARAMS ((cpp_reader *, U_CHAR *, U_CHAR *));
85 static struct operation cpp_lex PARAMS ((cpp_reader *, int));
86 extern HOST_WIDEST_INT cpp_parse_expr PARAMS ((cpp_reader *));
87 static HOST_WIDEST_INT cpp_parse_escape PARAMS ((cpp_reader *, U_CHAR **, HOST_WIDEST_INT));
88
89 #define ERROR 299
90 #define OROR 300
91 #define ANDAND 301
92 #define EQUAL 302
93 #define NOTEQUAL 303
94 #define LEQ 304
95 #define GEQ 305
96 #define LSH 306
97 #define RSH 307
98 #define NAME 308
99 #define INT 309
100 #define CHAR 310
101
102 #define LEFT_OPERAND_REQUIRED 1
103 #define RIGHT_OPERAND_REQUIRED 2
104 #define HAVE_VALUE 4
105 /* SKIP_OPERAND is set for '&&' '||' '?' and ':' when the
106    following operand should be short-circuited instead of evaluated.  */
107 #define SKIP_OPERAND 8
108 /*#define UNSIGNEDP 16*/
109
110 struct operation {
111     short op;
112     char rprio; /* Priority of op (relative to it right operand).  */
113     char flags;
114     char unsignedp;    /* true if value should be treated as unsigned */
115     HOST_WIDEST_INT value;        /* The value logically "right" of op.  */
116 };
117
118 /* Parse and convert an integer for #if.  Accepts decimal, hex, or octal
119    with or without size suffixes.  */
120
121 static struct operation
122 parse_number (pfile, start, end)
123      cpp_reader *pfile;
124      U_CHAR *start;
125      U_CHAR *end;
126 {
127   struct operation op;
128   U_CHAR *p = start;
129   int c;
130   unsigned HOST_WIDEST_INT n = 0, nd, MAX_over_base;
131   int base = 10;
132   int overflow = 0;
133   int digit, largest_digit = 0;
134   int spec_long = 0;
135
136   op.unsignedp = 0;
137
138   if (p[0] == '0')
139     {
140       if (end - start >= 3 && (p[1] == 'x' || p[1] == 'X'))
141         {
142           p += 2;
143           base = 16;
144         }
145       else
146         {
147           p += 1;
148           base = 8;
149         }
150     }
151
152   /* Some buggy compilers (e.g. MPW C) seem to need both casts.  */
153   MAX_over_base = (((unsigned HOST_WIDEST_INT) -1)
154                    / ((unsigned HOST_WIDEST_INT) base));
155
156   while (p < end)
157     {
158       c = *p++;
159
160       if (c >= '0' && c <= '9')
161         digit = c - '0';
162       else if (base == 16 && c >= 'a' && c <= 'f') /* FIXME: assumes ASCII */
163         digit = c - 'a' + 10;
164       else if (base == 16 && c >= 'A' && c <= 'F')
165         digit = c - 'A' + 10;
166       else if (c == '.')
167         {
168           /* It's a float since it contains a point.  */
169           cpp_error (pfile,
170                 "floating point numbers are not allowed in #if expressions");
171           goto error;
172         }
173       else
174         {
175           /* `l' means long, and `u' means unsigned.  */
176           for (;;)
177             {
178               if (c == 'l' || c == 'L')
179                   spec_long++;
180               else if (c == 'u' || c == 'U')
181                   op.unsignedp++;
182               else
183                 {
184                   /* Decrement p here so that the error for an invalid number
185                      will be generated below in the case where this is the
186                      last character in the buffer.  */
187                   p--;
188                   break;
189                 }
190               if (p == end)
191                 break;
192               c = *p++;
193             }
194           /* Don't look for any more digits after the suffixes.  */
195           break;
196         }
197       
198       if (largest_digit < digit)
199         largest_digit = digit;
200       nd = n * base + digit;
201       overflow |= MAX_over_base < n || nd < n;
202       n = nd;
203     }
204
205   if (p != end)
206     {
207       cpp_error (pfile, "invalid number in #if expression");
208       goto error;
209     }
210   else if (spec_long > (CPP_OPTIONS (pfile)->c89 ? 1 : 2))
211     {
212       cpp_error (pfile, "too many `l' suffixes in integer constant");
213       goto error;
214     }
215   else if (op.unsignedp > 1)
216     {
217       cpp_error (pfile, "too many `u' suffixes in integer constant");
218       goto error;
219     }
220   
221   if (base <= largest_digit)
222     cpp_pedwarn (pfile, "integer constant contains digits beyond the radix");
223
224   if (overflow)
225     cpp_pedwarn (pfile, "integer constant out of range");
226
227   /* If too big to be signed, consider it unsigned.  */
228   else if ((HOST_WIDEST_INT) n < 0 && ! op.unsignedp)
229     {
230       if (base == 10)
231         cpp_warning (pfile,
232                      "integer constant is so large that it is unsigned");
233       op.unsignedp = 1;
234     }
235
236   op.value = n;
237   op.op = INT;
238   return op;
239
240  error:
241   op.op = ERROR;
242   return op;
243 }
244
245 /* Parse and convert a character constant for #if.  Understands backslash
246    escapes (\n, \031) and multibyte characters (if so configured).  */
247 static struct operation
248 parse_charconst (pfile, start, end)
249      cpp_reader *pfile;
250      U_CHAR *start;
251      U_CHAR *end;
252 {
253   struct operation op;
254   HOST_WIDEST_INT result = 0;
255   int num_chars = 0;
256   int num_bits;
257   unsigned int width = MAX_CHAR_TYPE_SIZE, mask = MAX_CHAR_TYPE_MASK;
258   int max_chars;
259   U_CHAR *ptr = start;
260
261   /* FIXME: Should use reentrant multibyte functions.  */
262 #ifdef MULTIBYTE_CHARS
263   wchar_t c = (wchar_t)-1;
264   (void) mbtowc (NULL_PTR, NULL_PTR, 0);
265 #else
266   int c = -1;
267 #endif
268
269   if (*ptr == 'L')
270     {
271       ++ptr;
272       width = MAX_WCHAR_TYPE_SIZE, mask = MAX_WCHAR_TYPE_MASK;
273     }
274   max_chars = MAX_LONG_TYPE_SIZE / width;
275
276   ++ptr;  /* skip initial quote */
277
278   while (ptr < end)
279     {
280 #ifndef MULTIBYTE_CHARS
281       c = *ptr++;
282 #else
283       ptr += mbtowc (&c, ptr, end - ptr);
284 #endif
285       if (c == '\'' || c == '\0')
286         break;
287       else if (c == '\\')
288         {
289           /* Hopefully valid assumption: if mbtowc returns a backslash,
290              we are in initial shift state.  No valid escape-sequence
291              character can take us out of initial shift state or begin
292              an unshifted multibyte char, so cpp_parse_escape doesn't
293              need to know about multibyte chars.  */
294
295           c = cpp_parse_escape (pfile, &ptr, mask);
296           if (width < HOST_BITS_PER_INT
297               && (unsigned int) c >= (unsigned int)(1 << width))
298             cpp_pedwarn (pfile, "escape sequence out of range for character");
299         }
300           
301       /* Merge character into result; ignore excess chars.  */
302       if (++num_chars <= max_chars)
303         {
304           if (width < HOST_BITS_PER_INT)
305             result = (result << width) | (c & ((1 << width) - 1));
306           else
307             result = c;
308         }
309     }
310
311   if (num_chars == 0)
312     {
313       cpp_error (pfile, "empty character constant");
314       goto error;
315     }
316   else if (c != '\'')
317     {
318       /* cpp_get_token has already emitted an error if !traditional. */
319       if (! CPP_TRADITIONAL (pfile))
320         cpp_error (pfile, "malformatted character constant");
321       goto error;
322     }
323   else if (num_chars > max_chars)
324     {
325       cpp_error (pfile, "character constant too long");
326       goto error;
327     }
328   else if (num_chars != 1 && ! CPP_TRADITIONAL (pfile))
329     cpp_warning (pfile, "multi-character character constant");
330
331   /* If char type is signed, sign-extend the constant.  */
332   num_bits = num_chars * width;
333       
334   if (cpp_lookup (pfile, (const U_CHAR *)"__CHAR_UNSIGNED__",
335                   sizeof ("__CHAR_UNSIGNED__")-1, -1)
336       || ((result >> (num_bits - 1)) & 1) == 0)
337     op.value = result & ((unsigned HOST_WIDEST_INT) ~0
338                          >> (HOST_BITS_PER_WIDEST_INT - num_bits));
339   else
340     op.value = result | ~((unsigned HOST_WIDEST_INT) ~0
341                           >> (HOST_BITS_PER_WIDEST_INT - num_bits));
342
343   /* This is always a signed type.  */
344   op.unsignedp = 0;
345   op.op = CHAR;
346   return op;
347
348  error:
349   op.op = ERROR;
350   return op;
351 }
352
353
354 struct token {
355   const char *operator;
356   int token;
357 };
358
359 static struct token tokentab2[] = {
360   {"&&", ANDAND},
361   {"||", OROR},
362   {"<<", LSH},
363   {">>", RSH},
364   {"==", EQUAL},
365   {"!=", NOTEQUAL},
366   {"<=", LEQ},
367   {">=", GEQ},
368   {"++", ERROR},
369   {"--", ERROR},
370   {NULL, ERROR}
371 };
372
373 /* Read one token.  */
374
375 static struct operation
376 cpp_lex (pfile, skip_evaluation)
377      cpp_reader *pfile;
378      int skip_evaluation;
379 {
380   U_CHAR c;
381   struct token *toktab;
382   enum cpp_token token;
383   struct operation op;
384   U_CHAR *tok_start, *tok_end;
385   int old_written;
386
387  retry:
388
389   old_written = CPP_WRITTEN (pfile);
390   cpp_skip_hspace (pfile);
391   c = CPP_BUF_PEEK (CPP_BUFFER (pfile));
392   if (c == '#')
393     {
394       op.op = INT;
395       op.value = cpp_read_check_assertion (pfile);
396       return op;
397     }
398
399   if (c == '\n')
400     {
401       op.op = 0;
402       return op;
403     }
404
405   token = cpp_get_token (pfile);
406   tok_start = pfile->token_buffer + old_written;
407   tok_end = CPP_PWRITTEN (pfile);
408   pfile->limit = tok_start;
409   switch (token)
410   {
411     case CPP_EOF: /* Should not happen ...  */
412     case CPP_VSPACE:
413       op.op = 0;
414       return op;
415     case CPP_POP:
416       if (CPP_BUFFER (pfile)->fname != NULL)
417         {
418           op.op = 0;
419           return op;
420         }
421       cpp_pop_buffer (pfile);
422       goto retry;
423     case CPP_HSPACE:
424     case CPP_COMMENT: 
425       goto retry;
426     case CPP_NUMBER:
427       return parse_number (pfile, tok_start, tok_end);
428     case CPP_STRING:
429       cpp_error (pfile, "string constants not allowed in #if expressions");
430       op.op = ERROR;
431       return op;
432     case CPP_CHAR:
433       return parse_charconst (pfile, tok_start, tok_end);
434
435     case CPP_NAME:
436       op.op = INT;
437       op.unsignedp = 0;
438       op.value = 0;
439       if (strcmp (tok_start, "defined"))
440         {
441           if (CPP_WARN_UNDEF (pfile) && !skip_evaluation)
442             cpp_warning (pfile, "`%.*s' is not defined",
443                          (int) (tok_end - tok_start), tok_start);
444         }
445       else
446         {
447           int paren = 0, len;
448           cpp_buffer *ip = CPP_BUFFER (pfile);
449           U_CHAR *tok;
450           HASHNODE *hp;
451
452           cpp_skip_hspace (pfile);
453           if (*ip->cur == '(')
454             {
455               paren++;
456               ip->cur++;                        /* Skip over the paren */
457               cpp_skip_hspace (pfile);
458             }
459
460           if (!is_idstart[*ip->cur])
461             goto oops;
462           if (ip->cur[0] == 'L' && (ip->cur[1] == '\'' || ip->cur[1] == '"'))
463             goto oops;
464           tok = ip->cur;
465           while (is_idchar[*ip->cur])
466             ++ip->cur;
467           len = ip->cur - tok;
468           cpp_skip_hspace (pfile);
469           if (paren)
470             {
471               if (*ip->cur != ')')
472                 goto oops;
473               ++ip->cur;
474             }
475           hp = cpp_lookup (pfile, tok, len, -1);
476           if (hp != NULL)
477             {
478               if (hp->type == T_POISON)
479                 cpp_error (pfile, "attempt to use poisoned `%s'", hp->name);
480               else
481                 op.value = 1;
482             }
483         }
484       return op;
485
486     oops:
487       cpp_error (pfile, "`defined' without an identifier");
488       return op;
489
490     case CPP_OTHER:
491       /* See if it is a special token of length 2.  */
492       if (tok_start + 2 == tok_end)
493         {
494           for (toktab = tokentab2; toktab->operator != NULL; toktab++)
495             if (tok_start[0] == toktab->operator[0]
496                 && tok_start[1] == toktab->operator[1])
497                 break;
498           if (toktab->token == ERROR)
499             cpp_error (pfile, "`%s' not allowed in operand of `#if'",
500                        tok_start);
501           op.op = toktab->token; 
502           return op;
503         }
504       /* fall through */
505     default:
506       op.op = *tok_start;
507       return op;
508   }
509 }
510
511
512 /* Parse a C escape sequence.  STRING_PTR points to a variable
513    containing a pointer to the string to parse.  That pointer
514    is updated past the characters we use.  The value of the
515    escape sequence is returned.
516
517    A negative value means the sequence \ newline was seen,
518    which is supposed to be equivalent to nothing at all.
519
520    If \ is followed by a null character, we return a negative
521    value and leave the string pointer pointing at the null character.
522
523    If \ is followed by 000, we return 0 and leave the string pointer
524    after the zeros.  A value of 0 does not mean end of string.  */
525
526 static HOST_WIDEST_INT
527 cpp_parse_escape (pfile, string_ptr, result_mask)
528      cpp_reader *pfile;
529      U_CHAR **string_ptr;
530      HOST_WIDEST_INT result_mask;
531 {
532   register int c = *(*string_ptr)++;
533   switch (c)
534     {
535     case 'a':
536       return TARGET_BELL;
537     case 'b':
538       return TARGET_BS;
539     case 'e':
540     case 'E':
541       if (CPP_OPTIONS (pfile)->pedantic)
542         cpp_pedwarn (pfile, "non-ANSI-standard escape sequence, `\\%c'", c);
543       return TARGET_ESC;
544     case 'f':
545       return TARGET_FF;
546     case 'n':
547       return TARGET_NEWLINE;
548     case 'r':
549       return TARGET_CR;
550     case 't':
551       return TARGET_TAB;
552     case 'v':
553       return TARGET_VT;
554     case '\n':
555       return -2;
556     case 0:
557       (*string_ptr)--;
558       return 0;
559       
560     case '0':
561     case '1':
562     case '2':
563     case '3':
564     case '4':
565     case '5':
566     case '6':
567     case '7':
568       {
569         register HOST_WIDEST_INT i = c - '0';
570         register int count = 0;
571         while (++count < 3)
572           {
573             c = *(*string_ptr)++;
574             if (c >= '0' && c <= '7')
575               i = (i << 3) + c - '0';
576             else
577               {
578                 (*string_ptr)--;
579                 break;
580               }
581           }
582         if (i != (i & result_mask))
583           {
584             i &= result_mask;
585             cpp_pedwarn (pfile, "octal escape sequence out of range");
586           }
587         return i;
588       }
589     case 'x':
590       {
591         register unsigned HOST_WIDEST_INT i = 0, overflow = 0;
592         register int digits_found = 0, digit;
593         for (;;)
594           {
595             c = *(*string_ptr)++;
596             if (c >= '0' && c <= '9')
597               digit = c - '0';
598             else if (c >= 'a' && c <= 'f')
599               digit = c - 'a' + 10;
600             else if (c >= 'A' && c <= 'F')
601               digit = c - 'A' + 10;
602             else
603               {
604                 (*string_ptr)--;
605                 break;
606               }
607             overflow |= i ^ (i << 4 >> 4);
608             i = (i << 4) + digit;
609             digits_found = 1;
610           }
611         if (!digits_found)
612           cpp_error (pfile, "\\x used with no following hex digits");
613         if (overflow | (i != (i & result_mask)))
614           {
615             i &= result_mask;
616             cpp_pedwarn (pfile, "hex escape sequence out of range");
617           }
618         return i;
619       }
620     default:
621       return c;
622     }
623 }
624
625 static void
626 integer_overflow (pfile)
627      cpp_reader *pfile;
628 {
629   if (CPP_PEDANTIC (pfile))
630     cpp_pedwarn (pfile, "integer overflow in preprocessor expression");
631 }
632
633 static HOST_WIDEST_INT
634 left_shift (pfile, a, unsignedp, b)
635      cpp_reader *pfile;
636      HOST_WIDEST_INT a;
637      int unsignedp;
638      unsigned HOST_WIDEST_INT b;
639 {
640   if (b >= HOST_BITS_PER_WIDEST_INT)
641     {
642       if (! unsignedp && a != 0)
643         integer_overflow (pfile);
644       return 0;
645     }
646   else if (unsignedp)
647     return (unsigned HOST_WIDEST_INT) a << b;
648   else
649     {
650       HOST_WIDEST_INT l = a << b;
651       if (l >> b != a)
652         integer_overflow (pfile);
653       return l;
654     }
655 }
656
657 static HOST_WIDEST_INT
658 right_shift (pfile, a, unsignedp, b)
659      cpp_reader *pfile ATTRIBUTE_UNUSED;
660      HOST_WIDEST_INT a;
661      int unsignedp;
662      unsigned HOST_WIDEST_INT b;
663 {
664   if (b >= HOST_BITS_PER_WIDEST_INT)
665     return unsignedp ? 0 : a >> (HOST_BITS_PER_WIDEST_INT - 1);
666   else if (unsignedp)
667     return (unsigned HOST_WIDEST_INT) a >> b;
668   else
669     return a >> b;
670 }
671 \f
672 /* These priorities are all even, so we can handle associatively.  */
673 #define PAREN_INNER_PRIO 0
674 #define COMMA_PRIO 4
675 #define COND_PRIO (COMMA_PRIO+2)
676 #define OROR_PRIO (COND_PRIO+2)
677 #define ANDAND_PRIO (OROR_PRIO+2)
678 #define OR_PRIO (ANDAND_PRIO+2)
679 #define XOR_PRIO (OR_PRIO+2)
680 #define AND_PRIO (XOR_PRIO+2)
681 #define EQUAL_PRIO (AND_PRIO+2)
682 #define LESS_PRIO (EQUAL_PRIO+2)
683 #define SHIFT_PRIO (LESS_PRIO+2)
684 #define PLUS_PRIO (SHIFT_PRIO+2)
685 #define MUL_PRIO (PLUS_PRIO+2)
686 #define UNARY_PRIO (MUL_PRIO+2)
687 #define PAREN_OUTER_PRIO (UNARY_PRIO+2)
688
689 #define COMPARE(OP) \
690   top->unsignedp = 0;\
691   top->value = (unsigned1 || unsigned2) \
692   ? (unsigned HOST_WIDEST_INT) v1 OP (unsigned HOST_WIDEST_INT) v2 : (v1 OP v2)
693
694 /* Parse and evaluate a C expression, reading from PFILE.
695    Returns the value of the expression.  */
696
697 HOST_WIDEST_INT
698 cpp_parse_expr (pfile)
699      cpp_reader *pfile;
700 {
701   /* The implementation is an operator precedence parser,
702      i.e. a bottom-up parser, using a stack for not-yet-reduced tokens.
703
704      The stack base is 'stack', and the current stack pointer is 'top'.
705      There is a stack element for each operator (only),
706      and the most recently pushed operator is 'top->op'.
707      An operand (value) is stored in the 'value' field of the stack
708      element of the operator that precedes it.
709      In that case the 'flags' field has the HAVE_VALUE flag set.  */
710
711 #define INIT_STACK_SIZE 20
712   struct operation init_stack[INIT_STACK_SIZE];
713   struct operation *stack = init_stack;
714   struct operation *limit = stack + INIT_STACK_SIZE;
715   register struct operation *top = stack;
716   int lprio, rprio = 0;
717   int skip_evaluation = 0;
718
719   top->rprio = 0;
720   top->flags = 0;
721   for (;;)
722     {
723       struct operation op;
724       char flags = 0;
725
726       /* Read a token */
727       op =  cpp_lex (pfile, skip_evaluation);
728
729       /* See if the token is an operand, in which case go to set_value.
730          If the token is an operator, figure out its left and right
731          priorities, and then goto maybe_reduce.  */
732
733       switch (op.op)
734         {
735         case NAME:
736           cpp_fatal (pfile, "internal error: cpp_lex returns a NAME");
737           goto syntax_error;
738         case INT:  case CHAR:
739           top->value = op.value;
740           top->unsignedp = op.unsignedp;
741           goto set_value;
742         case 0:
743           lprio = 0;  goto maybe_reduce;
744         case '+':  case '-':
745           /* Is this correct if unary ? FIXME */
746           flags = RIGHT_OPERAND_REQUIRED;
747           lprio = PLUS_PRIO;  rprio = lprio + 1;  goto maybe_reduce;
748         case '!':  case '~':
749           flags = RIGHT_OPERAND_REQUIRED;
750           rprio = UNARY_PRIO;  lprio = rprio + 1;  goto maybe_reduce;
751         case '*':  case '/':  case '%':
752           lprio = MUL_PRIO;  goto binop;
753         case '<':  case '>':  case LEQ:  case GEQ:
754           lprio = LESS_PRIO;  goto binop;
755         case EQUAL:  case NOTEQUAL:
756           lprio = EQUAL_PRIO;  goto binop;
757         case LSH:  case RSH:
758           lprio = SHIFT_PRIO;  goto binop;
759         case '&':  lprio = AND_PRIO;  goto binop;
760         case '^':  lprio = XOR_PRIO;  goto binop;
761         case '|':  lprio = OR_PRIO;  goto binop;
762         case ANDAND:  lprio = ANDAND_PRIO;  goto binop;
763         case OROR:  lprio = OROR_PRIO;  goto binop;
764         case ',':
765           lprio = COMMA_PRIO;  goto binop;
766         case '(':
767           lprio = PAREN_OUTER_PRIO;  rprio = PAREN_INNER_PRIO;
768           goto maybe_reduce;
769         case ')':
770           lprio = PAREN_INNER_PRIO;  rprio = PAREN_OUTER_PRIO;
771           goto maybe_reduce;
772         case ':':
773           lprio = COND_PRIO;  rprio = COND_PRIO;
774           goto maybe_reduce;
775         case '?':
776           lprio = COND_PRIO + 1;  rprio = COND_PRIO;
777           goto maybe_reduce;
778         case ERROR:
779           goto syntax_error;
780         binop:
781           flags = LEFT_OPERAND_REQUIRED|RIGHT_OPERAND_REQUIRED;
782           rprio = lprio + 1;
783           goto maybe_reduce;
784         default:
785           cpp_error (pfile, "invalid character in #if");
786           goto syntax_error;
787         }
788
789     set_value:
790       /* Push a value onto the stack.  */
791       if (top->flags & HAVE_VALUE)
792         {
793           cpp_error (pfile, "syntax error in #if");
794           goto syntax_error;
795         }
796       top->flags |= HAVE_VALUE;
797       continue;
798
799     maybe_reduce:
800       /* Push an operator, and check if we can reduce now.  */
801       while (top->rprio > lprio)
802         {
803           HOST_WIDEST_INT v1 = top[-1].value, v2 = top[0].value;
804           int unsigned1 = top[-1].unsignedp, unsigned2 = top[0].unsignedp;
805           top--;
806           if ((top[1].flags & LEFT_OPERAND_REQUIRED)
807               && ! (top[0].flags & HAVE_VALUE))
808             {
809               cpp_error (pfile, "syntax error - missing left operand");
810               goto syntax_error;
811             }
812           if ((top[1].flags & RIGHT_OPERAND_REQUIRED)
813               && ! (top[1].flags & HAVE_VALUE))
814             {
815               cpp_error (pfile, "syntax error - missing right operand");
816               goto syntax_error;
817             }
818           /* top[0].value = (top[1].op)(v1, v2);*/
819           switch (top[1].op)
820             {
821             case '+':
822               if (!(top->flags & HAVE_VALUE))
823                 { /* Unary '+' */
824                   top->value = v2;
825                   top->unsignedp = unsigned2;
826                   top->flags |= HAVE_VALUE;
827                 }
828               else
829                 {
830                   top->value = v1 + v2;
831                   top->unsignedp = unsigned1 || unsigned2;
832                   if (! top->unsignedp && ! skip_evaluation
833                       && ! possible_sum_sign (v1, v2, top->value))
834                     integer_overflow (pfile);
835                 }
836               break;
837             case '-':
838               if (!(top->flags & HAVE_VALUE))
839                 { /* Unary '-' */
840                   top->value = - v2;
841                   if (!skip_evaluation && (top->value & v2) < 0 && !unsigned2)
842                     integer_overflow (pfile);
843                   top->unsignedp = unsigned2;
844                   top->flags |= HAVE_VALUE;
845                 }
846               else
847                 { /* Binary '-' */
848                   top->value = v1 - v2;
849                   top->unsignedp = unsigned1 || unsigned2;
850                   if (! top->unsignedp && ! skip_evaluation
851                       && ! possible_sum_sign (top->value, v2, v1))
852                     integer_overflow (pfile);
853                 }
854               break;
855             case '*':
856               top->unsignedp = unsigned1 || unsigned2;
857               if (top->unsignedp)
858                 top->value = (unsigned HOST_WIDEST_INT) v1 * v2;
859               else if (!skip_evaluation)
860                 {
861                   top->value = v1 * v2;
862                   if (v1
863                       && (top->value / v1 != v2
864                           || (top->value & v1 & v2) < 0))
865                     integer_overflow (pfile);
866                 }
867               break;
868             case '/':
869               if (skip_evaluation)
870                 break;
871               if (v2 == 0)
872                 {
873                   cpp_error (pfile, "division by zero in #if");
874                   v2 = 1;
875                 }
876               top->unsignedp = unsigned1 || unsigned2;
877               if (top->unsignedp)
878                 top->value = (unsigned HOST_WIDEST_INT) v1 / v2;
879               else
880                 {
881                   top->value = v1 / v2;
882                   if ((top->value & v1 & v2) < 0)
883                     integer_overflow (pfile);
884                 }
885               break;
886             case '%':
887               if (skip_evaluation)
888                 break;
889               if (v2 == 0)
890                 {
891                   cpp_error (pfile, "division by zero in #if");
892                   v2 = 1;
893                 }
894               top->unsignedp = unsigned1 || unsigned2;
895               if (top->unsignedp)
896                 top->value = (unsigned HOST_WIDEST_INT) v1 % v2;
897               else
898                 top->value = v1 % v2;
899               break;
900             case '!':
901               if (top->flags & HAVE_VALUE)
902                 {
903                   cpp_error (pfile, "syntax error");
904                   goto syntax_error;
905                 }
906               top->value = ! v2;
907               top->unsignedp = 0;
908               top->flags |= HAVE_VALUE;
909               break;
910             case '~':
911               if (top->flags & HAVE_VALUE)
912                 {
913                   cpp_error (pfile, "syntax error");
914                   goto syntax_error;
915                 }
916               top->value = ~ v2;
917               top->unsignedp = unsigned2;
918               top->flags |= HAVE_VALUE;
919               break;
920             case '<':  COMPARE(<);  break;
921             case '>':  COMPARE(>);  break;
922             case LEQ:  COMPARE(<=); break;
923             case GEQ:  COMPARE(>=); break;
924             case EQUAL:
925               top->value = (v1 == v2);
926               top->unsignedp = 0;
927               break;
928             case NOTEQUAL:
929               top->value = (v1 != v2);
930               top->unsignedp = 0;
931               break;
932             case LSH:
933               if (skip_evaluation)
934                 break;
935               top->unsignedp = unsigned1;
936               if (v2 < 0 && ! unsigned2)
937                 top->value = right_shift (pfile, v1, unsigned1, -v2);
938               else
939                 top->value = left_shift (pfile, v1, unsigned1, v2);
940               break;
941             case RSH:
942               if (skip_evaluation)
943                 break;
944               top->unsignedp = unsigned1;
945               if (v2 < 0 && ! unsigned2)
946                 top->value = left_shift (pfile, v1, unsigned1, -v2);
947               else
948                 top->value = right_shift (pfile, v1, unsigned1, v2);
949               break;
950 #define LOGICAL(OP) \
951               top->value = v1 OP v2;\
952               top->unsignedp = unsigned1 || unsigned2;
953             case '&':  LOGICAL(&); break;
954             case '^':  LOGICAL(^);  break;
955             case '|':  LOGICAL(|);  break;
956             case ANDAND:
957               top->value = v1 && v2;  top->unsignedp = 0;
958               if (!v1) skip_evaluation--;
959               break;
960             case OROR:
961               top->value = v1 || v2;  top->unsignedp = 0;
962               if (v1) skip_evaluation--;
963               break;
964             case ',':
965               if (CPP_PEDANTIC (pfile))
966                 cpp_pedwarn (pfile, "comma operator in operand of `#if'");
967               top->value = v2;
968               top->unsignedp = unsigned2;
969               break;
970             case '(':  case '?':
971               cpp_error (pfile, "syntax error in #if");
972               goto syntax_error;
973             case ':':
974               if (top[0].op != '?')
975                 {
976                   cpp_error (pfile,
977                              "syntax error ':' without preceding '?'");
978                   goto syntax_error;
979                 }
980               else if (! (top[1].flags & HAVE_VALUE)
981                        || !(top[-1].flags & HAVE_VALUE)
982                        || !(top[0].flags & HAVE_VALUE))
983                 {
984                   cpp_error (pfile, "bad syntax for ?: operator");
985                   goto syntax_error;
986                 }
987               else
988                 {
989                   top--;
990                   if (top->value) skip_evaluation--;
991                   top->value = top->value ? v1 : v2;
992                   top->unsignedp = unsigned1 || unsigned2;
993                 }
994               break;
995             case ')':
996               if ((top[1].flags & HAVE_VALUE)
997                   || ! (top[0].flags & HAVE_VALUE)
998                   || top[0].op != '('
999                   || (top[-1].flags & HAVE_VALUE))
1000                 {
1001                   cpp_error (pfile, "mismatched parentheses in #if");
1002                   goto syntax_error;
1003                 }
1004               else
1005                 {
1006                   top--;
1007                   top->value = v1;
1008                   top->unsignedp = unsigned1;
1009                   top->flags |= HAVE_VALUE;
1010                 }
1011               break;
1012             default:
1013               cpp_error (pfile,
1014                          (top[1].op >= ' ' && top[1].op <= '~'
1015                           ? "unimplemented operator '%c'\n"
1016                           : "unimplemented operator '\\%03o'\n"),
1017                          top[1].op);
1018             }
1019         }
1020       if (op.op == 0)
1021         {
1022           if (top != stack)
1023             cpp_error (pfile, "internal error in #if expression");
1024           if (stack != init_stack)
1025             free (stack);
1026           return top->value;
1027         }
1028       top++;
1029       
1030       /* Check for and handle stack overflow.  */
1031       if (top == limit)
1032         {
1033           struct operation *new_stack;
1034           int old_size = (char *) limit - (char *) stack;
1035           int new_size = 2 * old_size;
1036           if (stack != init_stack)
1037             new_stack = (struct operation *) xrealloc (stack, new_size);
1038           else
1039             {
1040               new_stack = (struct operation *) xmalloc (new_size);
1041               bcopy ((char *) stack, (char *) new_stack, old_size);
1042             }
1043           stack = new_stack;
1044           top = (struct operation *) ((char *) new_stack + old_size);
1045           limit = (struct operation *) ((char *) new_stack + new_size);
1046         }
1047       
1048       top->flags = flags;
1049       top->rprio = rprio;
1050       top->op = op.op;
1051       if ((op.op == OROR && top[-1].value)
1052           || (op.op == ANDAND && !top[-1].value)
1053           || (op.op == '?' && !top[-1].value))
1054         {
1055           skip_evaluation++;
1056         }
1057       else if (op.op == ':')
1058         {
1059           if (top[-2].value) /* Was condition true? */
1060             skip_evaluation++;
1061           else
1062             skip_evaluation--;
1063         }
1064     }
1065  syntax_error:
1066   if (stack != init_stack)
1067     free (stack);
1068   skip_rest_of_line (pfile);
1069   return 0;
1070 }