home *** CD-ROM | disk | FTP | other *** search
/ Geek Gadgets 1 / ADE-1.bin / ade-dist / gcc-2.7.2.1-base.tgz / gcc-2.7.2.1-base.tar / fsf / gcc / cppexp.c < prev    next >
C/C++ Source or Header  |  1995-11-07  |  25KB  |  998 lines

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