/***********************************************************************
* *
* This software is part of the ast package *
* Copyright (c) 1985-2011 AT&T Intellectual Property *
* and is licensed under the *
* Eclipse Public License, Version 1.0 *
* by AT&T Intellectual Property *
* *
* A copy of the License is available at *
* (with md5 checksum b35adb5213ca9657e911e9befb180842) *
* *
* Information and Software Systems Research *
* AT&T Research *
* Florham Park NJ *
* *
* Glenn Fowler <gsf@research.att.com> *
* David Korn <dgk@research.att.com> *
* Phong Vo <kpv@research.att.com> *
* *
***********************************************************************/
#pragma prototyped
/*
* G. S. Fowler
* D. G. Korn
* AT&T Bell Laboratories
*
* long integer arithmetic expression evaluator
* long constants may be represented as:
*
* 0ooo octal
* 0[xX]hhh hexadecimal
* ddd decimal
* n#ccc base n, 2 <= b <= 36
*
* NOTE: all operands are evaluated as both the parse
* and evaluation are done on the fly
*/
#include <ast.h>
#include <ctype.h>
typedef struct /* expression handle */
{
long (*convert)(const char*, char**, void*);
} Expr_t;
/*
* set error message string
*/
static long
{
return(0);
}
/*
* evaluate a subexpression with precedence
*/
static long
{
register int c;
register long n;
register long x;
char* pos;
switch (c)
{
case 0:
if (!precedence) return(0);
case '-':
break;
case '+':
break;
case '!':
break;
case '~':
break;
default:
n = 0;
operand = 0;
break;
}
for (;;)
{
{
case 0:
goto done;
case ')':
goto done;
case '(':
{
}
operand = 1;
continue;
case '?':
{
if (!n) n = x;
}
else
{
{
}
if (n)
{
n = x;
}
}
break;
case ':':
goto done;
case '|':
{
n = n || x;
}
else
{
n |= x;
}
break;
case '^':
n ^= x;
break;
case '&':
{
n = n && x;
}
else
{
n &= x;
}
break;
case '=':
case '!':
if (c == '=') n = n == x;
else n = n != x;
break;
case '<':
case '>':
{
if (c == '<') n <<= x;
else n >>= x;
}
else
{
{
if (c == '<') n = n <= x;
else n = n >= x;
}
else
{
if (c == '<') n = n < x;
else n = n > x;
}
}
break;
case '+':
case '-':
if (c == '+') n += x;
else n -= x;
break;
case '*':
case '/':
case '%':
if (c == '*') n *= x;
else if (c == '/') n /= x;
else n %= x;
break;
default:
if (isspace(c)) continue;
goto gotoperand;
}
}
done:
return(n);
}
/*
* evaluate an integer arithmetic expression in s
*
* (long)(*convert)(const char* string, char** end, void* handle)
* is a user supplied conversion routine that is called when unknown
* chars are encountered; string points to the part to be
* converted and end is adjusted to point to the next non-converted
* character; if string is 0 then end points to an error message string
*
* NOTE: (*convert)() may call strexpr(ex, )
*/
long
{
long n;
{
n = 0;
}
return(n);
}