#include <stdlib.h>
#include <ctype.h>
#include <stdio.h>
#include <string.h>
#include <math.h>

#define DELIMITER       1
#define VARIABLE        2
#define INTEGER_LITERAL 3
#define TRUE            1
#define FALSE           0

char Current_Token[80],*Expression;
int Token_Type;

void Eval_1(int *Answer), Eval_2(int *Answer), Eval_3(int *Answer);
void Eval_4(int *Answer), Eval_5(int *Answer), Eval_6(int *Answer);
void ParseError(int Error);
int Get_Token(void);
int Equal(char *S1,char *S2);


main (argc,argv)

int argc;
char **argv;

{
   int i,answer;

   for(i=2;i<=argc;i++)
   {
      Expression = argv[i-1];
      Eval_1(&answer);
      printf("\n%s =  %d\n",argv[i-1],answer);
   }
}

int Equal(S1,S2)

char *S1,*S2;

{
   return(!strcmp(S1,S2));
}

void Eval_1(Answer)

int *Answer;

{
   if (Get_Token()) Eval_2(Answer);
   else ParseError(2);
}

/* Token In Current_Token, Exp Ptr to next item */

void Eval_2(Answer)

int *Answer;

{
   int Temp,OldAnswer;
   char Op[80],*OldPosition;

   Eval_3(Answer);

   OldAnswer = *Answer;
   OldPosition = Expression;

   do
   {  if (Get_Token())
      {
         strcpy(Op,Current_Token);
         if (Equal(Op,"|"))
         {
	    if (Get_Token())
	    {
	       Eval_3(&Temp);
               printf("Doing: %d || %d\n",*Answer,Temp);
	       OldAnswer = *Answer = Temp || *Answer;
	       OldPosition = Expression;
	    }
         }
         else
         {
            *Answer = OldAnswer;
            Expression = OldPosition;
         }
      }
      else Op[0] = '\0';
   }
   while (Equal(Op,"|") && *Expression);
}

void Eval_3(Answer)

int *Answer;

{
   int Temp,OldAnswer;
   char Op[80],*OldPosition;

   Eval_4(Answer);

   OldAnswer = *Answer;
   OldPosition = Expression;

   do
   {
      if (Get_Token())
      {
         strcpy(Op,Current_Token);
         if (Equal(Op,"&"))
         {
            if (Get_Token())
	    {
	       Eval_4(&Temp);
               printf("Doing: %d && %d\n",*Answer,Temp);
	       OldAnswer = *Answer = Temp && *Answer;
	       OldPosition = Expression;
	    }
         }
         else
         {
            Expression = OldPosition;
            *Answer = OldAnswer;
         }
      }
      else Op[0] = '\0';
   }
   while (Equal(Op,"&") && *Expression);
}

void Eval_4(Answer)

int *Answer;

{
   if (Equal(Current_Token,"-"))
   {
      if (Get_Token())
      {
	 Eval_5(Answer);
	 if (*Answer == 0) *Answer = 1;
	 else *Answer = 0;
      }
      else ParseError(3);
   }
   else Eval_5(Answer);
}

void Eval_5(Answer)

int *Answer;

{
   if (Equal(Current_Token,"("))
   {
      Get_Token();
      Eval_2(Answer);
      if (!Equal(Current_Token,")")) ParseError(1);
      printf("The Current Token: %s",Current_Token);
      Get_Token();
   }
   else Eval_6(Answer);
}

void Eval_6(Answer)

int *Answer;

{
   if (Token_Type == INTEGER_LITERAL) *Answer = atoi(Current_Token);
}

int Get_Token()

{

   char *Temp;

   Temp = Current_Token;

   if (*Expression)
   {
      if (isalpha(*Expression))
      {
	 Token_Type = VARIABLE;
	 while(isalpha(*Expression)) *Temp++ = *Expression++;
      }
      else if (isdigit(*Expression))
      {
         Token_Type = INTEGER_LITERAL;
         while(isdigit(*Expression)) *Temp++ = *Expression++;
      }
      else if (strchr("&|-()",*Expression))
      {
         *Temp++ = *Expression++;
	 Token_Type = DELIMITER;
      }
      else
      {
         return(0);
      }

      *Temp = '\0';
      return(1);

   }
   return(0);
}

void ParseError(int Error)
{
   static char *e[] = {
			 "Syntax Error",
			 "Unbalanced Paranthesis",
			 "No Expression Present"
			 "No Operand For Unary Minus"
			 "Incomplete Expression"
			 "Invalid Argument Type"
		      };
   printf("Error: %s",e[Error]);
}
