/*
Very Simple Compiler
Parser part
$Id: s-compile.c,v 1.1 1996/09/22 11:29:31 kono Exp kono $
*/
#include "s-compile.h"
void error(char *);
void expr();
void aexpr();
void mexpr();
void term();
int token();
char *ptr,*last_ptr,*before;
int value,lvalue;
int last_token;
int
token()
{
int c,d;
last_ptr = ptr; /* for error position */
c= *ptr;
if(!c) {
last_token = EOF;
return last_token;
}
ptr++;
if (c< =' ') { /* comment */
while(*ptr++);
ptr--;
last_token = EOF;
last_ptr = ptr;
return last_token;
}
if('0'< =c && c< ='9') { /* Decimal */
d = c-'0';
while(c= *ptr++) {
if('0'< =c && c< ='9') {
d = d*10 + (c - '0');
} else {
break;
}
}
c && ptr--;
value = d;
last_token = '0';
return last_token;
} else if ('a'< =c && c< ='z') { /* variable */
value = c-'a'; /* return variable reference */
last_token = 'v';
return last_token;
} else {
last_token = c;
return last_token;
return c;
}
}
void
expr()
{
int assign;
emit_comment();
aexpr();
assign = lvalue;
while(last_token!=EOF) {
switch(last_token) {
case '>':
emit_push();
aexpr();
emit_compare();
break;
case '=':
if(assign>=0) {
expr();
emit_store(assign);
return;
} else {
error("Bad assignment");
return;
}
case ')':
return;
case EOF:
return;
default:
error("Bad expression");
token();
return;
}
}
return;
}
void
aexpr()
{
emit_comment();
mexpr();
while(last_token!=EOF) {
switch(last_token) {
case '-':
emit_push();
mexpr();
emit_calc(O_SUB);
break;
case '+':
emit_push();
mexpr();
emit_calc(O_ADD);
break;
default:
return;
}
}
return;
}
void
mexpr()
{
int d;
emit_comment();
term();
while(last_token!=EOF) {
switch(last_token) {
case '*':
emit_push();
term();
emit_calc(O_MUL);
break;
case '/':
emit_push();
term();
emit_calc(O_DIV);
break;
default:
return;
}
}
return;
}
void
term()
{
int d;
lvalue= -1;
emit_comment();
token();
if(last_token==EOF) {
error("Term expected");
}
switch(last_token) {
case '0':
d = value;
emit_value(d);
token();
return;
case 'v':
d = lvalue = value;
emit_load(d);
token();
return;
case '(':
expr();
if(last_token != ')') {
error("Unbalanced parenthsis");
}
token();
return;
default:
token();
error("Unknown term");
return;
}
}
int
main()
{
int d;
char buf[BUFSIZ];
emit_intro();
while (fgets(buf,BUFSIZ,stdin)) {
ptr = buf;
before = buf;
printf("%s %s",comments,buf);
expr();
emit_print();
emit_comment();
}
emit_ending();
return 0;
}
void
error(s)
char *s;
{
fprintf(stderr,"%s on %s\n",s,last_ptr);
}
/* end */