]> oss.titaniummirror.com Git - msp430-gcc.git/blobdiff - gcc/tradcif.y
Imported gcc-4.4.3
[msp430-gcc.git] / gcc / tradcif.y
diff --git a/gcc/tradcif.y b/gcc/tradcif.y
deleted file mode 100644 (file)
index 953e2d6..0000000
+++ /dev/null
@@ -1,567 +0,0 @@
-/* Parse C expressions for CCCP.
-   Copyright (C) 1987, 2000, 2001 Free Software Foundation.
-   Adapted from expread.y of GDB by Paul Rubin, July 1986.
-   Adapted to ANSI C, Richard Stallman, Jan 1987
-   Dusted off, polished, and adapted for use as traditional
-   preprocessor only, Zack Weinberg, Jul 2000
-
-This program is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 2, or (at your option) any
-later version.
-
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
-
-/* Parse a C expression from text in a string  */
-   
-%{
-#include "config.h"
-#include "system.h"
-#include "intl.h"
-#include "tradcpp.h"
-#include <setjmp.h>
-
-  static int yylex PARAMS ((void));
-  static void yyerror PARAMS ((const char *msgid)) ATTRIBUTE_NORETURN;
-
-  static int parse_number PARAMS ((int));
-  static int parse_escape PARAMS ((const char **));
-
-  static int expression_value;
-  static jmp_buf parse_return_error;
-
-  /* During parsing of a C expression, the pointer to the next
-     character is in this variable.  */
-
-  static const char *lexptr;
-%}
-
-%union {
-  struct constant {long value; int unsignedp;} integer;
-  int voidval;
-  char *sval;
-}
-
-%type <integer> exp exp1 start
-%token <integer> INT CHAR
-%token <sval> NAME
-%token <integer> ERROR
-
-%right '?' ':'
-%left ','
-%left OR
-%left AND
-%left '|'
-%left '^'
-%left '&'
-%left EQUAL NOTEQUAL
-%left '<' '>' LEQ GEQ
-%left LSH RSH
-%left '+' '-'
-%left '*' '/' '%'
-%right UNARY
-
-/* %expect 40 */
-\f
-%%
-
-start   :      exp1
-               { expression_value = $1.value; }
-       ;
-
-/* Expressions, including the comma operator.  */
-exp1   :       exp
-       |       exp1 ',' exp
-                       { $$ = $3; }
-       ;
-
-/* Expressions, not including the comma operator.  */
-exp    :       '-' exp    %prec UNARY
-                       { $$.value = - $2.value;
-                         $$.unsignedp = $2.unsignedp; }
-       |       '!' exp    %prec UNARY
-                       { $$.value = ! $2.value;
-                         $$.unsignedp = 0; }
-       |       '+' exp    %prec UNARY
-                       { $$ = $2; }
-       |       '~' exp    %prec UNARY
-                       { $$.value = ~ $2.value;
-                         $$.unsignedp = $2.unsignedp; }
-       |       '(' exp1 ')'
-                       { $$ = $2; }
-       ;
-
-/* Binary operators in order of decreasing precedence.  */
-exp    :       exp '*' exp
-                       { $$.unsignedp = $1.unsignedp || $3.unsignedp;
-                         if ($$.unsignedp)
-                           $$.value = (unsigned) $1.value * $3.value;
-                         else
-                           $$.value = $1.value * $3.value; }
-       |       exp '/' exp
-                       { if ($3.value == 0)
-                           {
-                             error ("division by zero in #if");
-                             $3.value = 1;
-                           }
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp;
-                         if ($$.unsignedp)
-                           $$.value = (unsigned) $1.value / $3.value;
-                         else
-                           $$.value = $1.value / $3.value; }
-       |       exp '%' exp
-                       { if ($3.value == 0)
-                           {
-                             error ("division by zero in #if");
-                             $3.value = 1;
-                           }
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp;
-                         if ($$.unsignedp)
-                           $$.value = (unsigned) $1.value % $3.value;
-                         else
-                           $$.value = $1.value % $3.value; }
-       |       exp '+' exp
-                       { $$.value = $1.value + $3.value;
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp; }
-       |       exp '-' exp
-                       { $$.value = $1.value - $3.value;
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp; }
-       |       exp LSH exp
-                       { $$.unsignedp = $1.unsignedp;
-                         if ($$.unsignedp)
-                           $$.value = (unsigned) $1.value << $3.value;
-                         else
-                           $$.value = $1.value << $3.value; }
-       |       exp RSH exp
-                       { $$.unsignedp = $1.unsignedp;
-                         if ($$.unsignedp)
-                           $$.value = (unsigned) $1.value >> $3.value;
-                         else
-                           $$.value = $1.value >> $3.value; }
-       |       exp EQUAL exp
-                       { $$.value = ($1.value == $3.value);
-                         $$.unsignedp = 0; }
-       |       exp NOTEQUAL exp
-                       { $$.value = ($1.value != $3.value);
-                         $$.unsignedp = 0; }
-       |       exp LEQ exp
-                       { $$.unsignedp = 0;
-                         if ($1.unsignedp || $3.unsignedp)
-                           $$.value =
-                             (unsigned) $1.value <= (unsigned) $3.value;
-                         else
-                           $$.value = $1.value <= $3.value; }
-       |       exp GEQ exp
-                       { $$.unsignedp = 0;
-                         if ($1.unsignedp || $3.unsignedp)
-                           $$.value =
-                             (unsigned) $1.value >= (unsigned) $3.value;
-                         else
-                           $$.value = $1.value >= $3.value; }
-       |       exp '<' exp
-                       { $$.unsignedp = 0;
-                         if ($1.unsignedp || $3.unsignedp)
-                           $$.value =
-                             (unsigned) $1.value < (unsigned) $3.value;
-                         else
-                           $$.value = $1.value < $3.value; }
-       |       exp '>' exp
-                       { $$.unsignedp = 0;
-                         if ($1.unsignedp || $3.unsignedp)
-                           $$.value =
-                             (unsigned) $1.value > (unsigned) $3.value;
-                         else
-                           $$.value = $1.value > $3.value; }
-       |       exp '&' exp
-                       { $$.value = $1.value & $3.value;
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp; }
-       |       exp '^' exp
-                       { $$.value = $1.value ^ $3.value;
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp; }
-       |       exp '|' exp
-                       { $$.value = $1.value | $3.value;
-                         $$.unsignedp = $1.unsignedp || $3.unsignedp; }
-       |       exp AND exp
-                       { $$.value = ($1.value && $3.value);
-                         $$.unsignedp = 0; }
-       |       exp OR exp
-                       { $$.value = ($1.value || $3.value);
-                         $$.unsignedp = 0; }
-       |       exp '?' exp ':' exp
-                       { $$.value = $1.value ? $3.value : $5.value;
-                         $$.unsignedp = $3.unsignedp || $5.unsignedp; }
-       |       INT
-                       { $$ = yylval.integer; }
-       |       CHAR
-                       { $$ = yylval.integer; }
-       |       NAME
-                       { $$.value = 0;
-                         $$.unsignedp = 0; }
-       |       '#'     { $$.value =
-                           test_assertion ((unsigned char **) &lexptr); }
-       ;
-%%
-\f
-/* Take care of parsing a number (anything that starts with a digit).
-   Set yylval and return the token type; update lexptr.
-   LEN is the number of characters in it.  */
-
-/* maybe needs to actually deal with floating point numbers */
-
-static int
-parse_number (olen)
-     int olen;
-{
-  const char *p = lexptr;
-  long n = 0;
-  int c;
-  int base = 10;
-  int len = olen;
-
-  for (c = 0; c < len; c++)
-    if (p[c] == '.') {
-      /* It's a float since it contains a point.  */
-      yyerror ("floating point numbers not allowed in #if expressions");
-      return ERROR;
-    }
-
-  /* Traditionally, all numbers are signed.  However, we make it
-     unsigned if requested with a suffix.  */
-  yylval.integer.unsignedp = 0;
-
-  if (len >= 3 && (!strncmp (p, "0x", 2) || !strncmp (p, "0X", 2))) {
-    p += 2;
-    base = 16;
-    len -= 2;
-  }
-  else if (*p == '0')
-    base = 8;
-
-  while (len > 0) {
-    c = *p++;
-    len--;
-    if (ISUPPER (c))
-      c = TOLOWER (c);
-
-    if (ISDIGIT (c)
-       || (base == 16 && ISXDIGIT (c))) {
-      n = (n * base) + hex_value (c);
-    } else {
-      /* `l' means long, and `u' means unsigned.  */
-      while (1) {
-       if (c == 'l' || c == 'L')
-         ;
-       else if (c == 'u' || c == 'U')
-         yylval.integer.unsignedp = 1;
-       else
-         break;
-
-       if (len == 0)
-         break;
-       c = *p++;
-       len--;
-      }
-      /* Don't look for any more digits after the suffixes.  */
-      break;
-    }
-  }
-
-  if (len != 0) {
-    yyerror ("invalid number in #if expression");
-    return ERROR;
-  }
-
-  lexptr = p;
-  yylval.integer.value = n;
-  return INT;
-}
-
-struct token {
-  const char *const operator;
-  const int token;
-};
-
-#ifndef NULL
-#define NULL 0
-#endif
-
-static const struct token tokentab2[] = {
-  {"&&", AND},
-  {"||", OR},
-  {"<<", LSH},
-  {">>", RSH},
-  {"==", EQUAL},
-  {"!=", NOTEQUAL},
-  {"<=", LEQ},
-  {">=", GEQ},
-  {NULL, ERROR}
-};
-
-/* Read one token, getting characters through lexptr.  */
-
-static int
-yylex ()
-{
-  int c;
-  int namelen;
-  const char *tokstart;
-  const struct token *toktab;
-
- retry:
-
-  tokstart = lexptr;
-  c = *tokstart;
-  /* See if it is a special token of length 2.  */
-  for (toktab = tokentab2; toktab->operator != NULL; toktab++)
-    if (c == *toktab->operator && tokstart[1] == toktab->operator[1]) {
-      lexptr += 2;
-      return toktab->token;
-    }
-
-  switch (c) {
-  case 0:
-    return 0;
-    
-  case ' ':
-  case '\t':
-  case '\r':
-  case '\n':
-    lexptr++;
-    goto retry;
-    
-  case '\'':
-    lexptr++;
-    c = *lexptr++;
-    if (c == '\\')
-      c = parse_escape (&lexptr);
-
-    /* Sign-extend the constant if chars are signed on target machine.  */
-    {
-      if (flag_signed_char == 0
-         || ((c >> (CHAR_TYPE_SIZE - 1)) & 1) == 0)
-       yylval.integer.value = c & ((1 << CHAR_TYPE_SIZE) - 1);
-      else
-       yylval.integer.value = c | ~((1 << CHAR_TYPE_SIZE) - 1);
-    }
-
-    yylval.integer.unsignedp = 0;
-    c = *lexptr++;
-    if (c != '\'') {
-      yyerror ("invalid character constant in #if");
-      return ERROR;
-    }
-    
-    return CHAR;
-
-    /* some of these chars are invalid in constant expressions;
-       maybe do something about them later */
-  case '/':
-  case '+':
-  case '-':
-  case '*':
-  case '%':
-  case '|':
-  case '&':
-  case '^':
-  case '~':
-  case '!':
-  case '@':
-  case '<':
-  case '>':
-  case '(':
-  case ')':
-  case '[':
-  case ']':
-  case '.':
-  case '?':
-  case ':':
-  case '=':
-  case '{':
-  case '}':
-  case ',':
-  case '#':
-    lexptr++;
-    return c;
-    
-  case '"':
-    yyerror ("double quoted strings not allowed in #if expressions");
-    return ERROR;
-  }
-  if (ISDIGIT (c)) {
-    /* It's a number */
-    for (namelen = 0;
-        c = tokstart[namelen], is_idchar (c) || c == '.'; 
-        namelen++)
-      ;
-    return parse_number (namelen);
-  }
-  
-  if (!is_idstart (c)) {
-    yyerror ("invalid token in expression");
-    return ERROR;
-  }
-  
-  /* It is a name.  See how long it is.  */
-  
-  for (namelen = 0;
-       is_idchar (tokstart[namelen]);
-       namelen++)
-    ;
-  
-  lexptr += namelen;
-  return NAME;
-}
-
-
-/* Parse a C escape sequence.  STRING_PTR points to a variable
-   containing a pointer to the string to parse.  That pointer
-   is updated past the characters we use.  The value of the
-   escape sequence is returned.
-
-   A negative value means the sequence \ newline was seen,
-   which is supposed to be equivalent to nothing at all.
-
-   If \ is followed by a null character, we return a negative
-   value and leave the string pointer pointing at the null character.
-
-   If \ is followed by 000, we return 0 and leave the string pointer
-   after the zeros.  A value of 0 does not mean end of string.  */
-
-static int
-parse_escape (string_ptr)
-     const char **string_ptr;
-{
-  int c = *(*string_ptr)++;
-  switch (c)
-    {
-    case 'a':
-      return TARGET_BELL;
-    case 'b':
-      return TARGET_BS;
-    case 'e':
-      return 033;
-    case 'f':
-      return TARGET_FF;
-    case 'n':
-      return TARGET_NEWLINE;
-    case 'r':
-      return TARGET_CR;
-    case 't':
-      return TARGET_TAB;
-    case 'v':
-      return TARGET_VT;
-    case '\n':
-      return -2;
-    case 0:
-      (*string_ptr)--;
-      return 0;
-    case '^':
-      c = *(*string_ptr)++;
-      if (c == '\\')
-       c = parse_escape (string_ptr);
-      if (c == '?')
-       return 0177;
-      return (c & 0200) | (c & 037);
-      
-    case '0':
-    case '1':
-    case '2':
-    case '3':
-    case '4':
-    case '5':
-    case '6':
-    case '7':
-      {
-       int i = c - '0';
-       int count = 0;
-       while (++count < 3)
-         {
-           c = *(*string_ptr)++;
-           if (c >= '0' && c <= '7')
-             i = (i << 3) + c - '0';
-           else
-             {
-               (*string_ptr)--;
-               break;
-             }
-         }
-       if ((i & ~((1 << CHAR_TYPE_SIZE) - 1)) != 0)
-         {
-           i &= (1 << CHAR_TYPE_SIZE) - 1;
-           warning ("octal character constant does not fit in a byte");
-         }
-       return i;
-      }
-    case 'x':
-      {
-       int i = 0;
-       for (;;)
-         {
-           c = *(*string_ptr)++;
-           if (hex_p (c))
-             i = (i << 4) + hex_value (c);
-           else
-             {
-               (*string_ptr)--;
-               break;
-             }
-         }
-       if ((i & ~((1 << BITS_PER_UNIT) - 1)) != 0)
-         {
-           i &= (1 << BITS_PER_UNIT) - 1;
-           warning ("hex character constant does not fit in a byte");
-         }
-       return i;
-      }
-    default:
-      return c;
-    }
-}
-
-static void
-yyerror (msgid)
-     const char *msgid;
-{
-  error ("%s", _(msgid));
-  longjmp (parse_return_error, 1);
-}
-\f
-/* This page contains the entry point to this file.  */
-
-/* Parse STRING as an expression, and complain if this fails
-   to use up all of the contents of STRING.  */
-/* We do not support C comments.  They should be removed before
-   this function is called.  */
-
-int
-parse_c_expression (string)
-     const char *string;
-{
-  lexptr = string;
-  
-  if (lexptr == 0 || *lexptr == 0) {
-    error ("empty #if expression");
-    return 0;                  /* don't include the #if group */
-  }
-
-  /* if there is some sort of scanning error, just return 0 and assume
-     the parsing routine has printed an error message somewhere.
-     there is surely a better thing to do than this.     */
-  if (setjmp (parse_return_error))
-    return 0;
-
-  if (yyparse ())
-    return 0;                  /* actually this is never reached
-                                  the way things stand. */
-  if (*lexptr)
-    error ("Junk after end of expression.");
-
-  return expression_value;     /* set by yyparse () */
-}