197403Sobrien%{ 297403Sobrien# include <stdio.h> 397403Sobrien# include <ctype.h> 497403Sobrien 597403Sobrienint regs[26]; 697403Sobrienint base; 797403Sobrien 897403Sobrienextern int yylex(void); 997403Sobrienstatic void yyerror(const char *s); 1097403Sobrien 1197403Sobrien%} 1297403Sobrien 1397403Sobrien%start list 1497403Sobrien 1597403Sobrien%token DIGIT LETTER 1697403Sobrien 1797403Sobrien%left '|' 1897403Sobrien%left '&' 1997403Sobrien%left '+' '-' 2097403Sobrien%left '*' '/' '%' 2197403Sobrien%left UMINUS /* supplies precedence for unary minus */ 2297403Sobrien 2397403Sobrien%% /* beginning of rules section */ 2497403Sobrien 2597403Sobrienlist : /* empty */ 2697403Sobrien | list stat '\n' 2797403Sobrien | list error '\n' 2897403Sobrien { yyerrok ; } 2997403Sobrien ; 3097403Sobrien 3197403Sobrienstat : expr 3297403Sobrien { printf("%d\n",$1);} 3397403Sobrien | LETTER '=' expr 3497403Sobrien { regs[$1] = $3; } 3597403Sobrien ; 3697403Sobrien 3797403Sobrienexpr : '(' expr ')' 3897403Sobrien { $$ = $2; } 3997403Sobrien | expr '+' expr 4097403Sobrien { $$ = $1 + $3; } 4197403Sobrien | expr '-' expr 4297403Sobrien { $$ = $1 - $3; } 4397403Sobrien | expr '*' expr 4497403Sobrien { $$ = $1 * $3; } 4597403Sobrien | expr '/' expr 4697403Sobrien { $$ = $1 / $3; } 4797403Sobrien | expr '%' expr 4897403Sobrien { $$ = $1 % $3; } 4997403Sobrien | expr '&' expr 5097403Sobrien { $$ = $1 & $3; } 5197403Sobrien | expr '|' expr 5297403Sobrien { $$ = $1 | $3; } 5397403Sobrien | '-' expr %prec UMINUS 5497403Sobrien { $$ = - $2; } 5597403Sobrien | LETTER 5697403Sobrien { $$ = regs[$1]; } 5797403Sobrien | number 5897403Sobrien ; 5997403Sobrien 6097403Sobriennumber: DIGIT 6197403Sobrien { $$ = $1; base = ($1==0) ? 8 : 10; } 6297403Sobrien | number DIGIT 6397403Sobrien { $$ = base * $1 + $2; } 6497403Sobrien ; 6597403Sobrien 6697403Sobrien%% /* start of programs */ 6797403Sobrien 6897403Sobrienint 6997403Sobrienmain (void) 7097403Sobrien{ 7197403Sobrien while(!feof(stdin)) { 7297403Sobrien yyparse(); 7397403Sobrien } 7497403Sobrien return 0; 7597403Sobrien} 7697403Sobrien 7797403Sobrienstatic void 7897403Sobrienyyerror(const char *s) 7997403Sobrien{ 8097403Sobrien fprintf(stderr, "%s\n", s); 8197403Sobrien} 8297403Sobrien 8397403Sobrienint 8497403Sobrienyylex(void) 8597403Sobrien{ 8697403Sobrien /* lexical analysis routine */ 8797403Sobrien /* returns LETTER for a lower case letter, yylval = 0 through 25 */ 8897403Sobrien /* return DIGIT for a digit, yylval = 0 through 9 */ 8997403Sobrien /* all other characters are returned immediately */ 9097403Sobrien 9197403Sobrien int c; 9297403Sobrien 9397403Sobrien while( (c=getchar()) == ' ' ) { /* skip blanks */ } 9497403Sobrien 9597403Sobrien /* c is now nonblank */ 9697403Sobrien 97102782Skan if( islower( c )) { 9897403Sobrien yylval = c - 'a'; 9997403Sobrien return ( LETTER ); 10097403Sobrien } 10197403Sobrien if( isdigit( c )) { 10297403Sobrien yylval = c - '0'; 10397403Sobrien return ( DIGIT ); 10497403Sobrien } 10597403Sobrien return( c ); 10697403Sobrien} 107102782Skan