Untitled

                Never    
C
       
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

// Token types
typedef enum {
    UNKNOWN,
    END,
    ENDFILE,
    INT,
    ID,
    ADDSUB,
    MULDIV,
    ASSIGN,
    INCDEC,
    LPAREN,
    RPAREN,
    AND,
    OR,
    XOR
} TokenSet;
#define TBLSIZE 64

// Set PRINTERR to 1 to print error message while calling error()
// Make sure you set PRINTERR to 0 before you submit your code
#define PRINTERR 1

#define MAXLEN 256
// Call this macro to print error message and exit the program
// This will also print where you called it in your program
#define error(errorNum)                                                       \
    {                                                                         \
        if (PRINTERR)                                                         \
            fprintf(stderr, "error() called at %s:%d: ", __FILE__, __LINE__); \
        err(errorNum);                                                        \
    }

// Error types
typedef enum {
    UNDEFINED,
    MISPAREN,
    NOTNUMID,
    NOTFOUND,
    RUNOUT,
    NOTLVAL,
    DIVZERO,
    SYNTAXERR
} ErrorType;

// Structure of the symbol table
typedef struct {
    int val;
    char name[MAXLEN];
} Symbol;

// Structure of a tree node
typedef struct _Node {
    TokenSet data;
    int val;
    char lexeme[MAXLEN];
    struct _Node *left;
    struct _Node *right;
} BTNode;

// The symbol table
extern Symbol table[TBLSIZE];

// Initialize the symbol table with builtin variables
extern void initTable(void);

// Get the value of a variable
extern int getval(char *str);

// Set the value of a variable
extern int setval(char *str, int val);

// Make a new node according to token type and lexeme
extern BTNode *makeNode(TokenSet tok, const char *lexe);

// Free the syntax tree
extern void freeTree(BTNode *root);
// Evaluate the syntax tree
extern int evaluateTree(BTNode *root);

// Print the syntax tree in prefix
extern void printPrefix(BTNode *root);
extern BTNode *factor(void);
extern BTNode *term(void);
extern BTNode *term_tail(BTNode *left);
extern BTNode *expr(void);
extern BTNode *expr_tail(BTNode *left);
extern BTNode *assign_expr();
extern BTNode *or_expr();
extern BTNode *or_expr_tail(BTNode *left);
extern BTNode *xor_expr();
extern BTNode *xor_expr_tail(BTNode *left);
extern BTNode *and_expr();
extern BTNode *and_expr_tail(BTNode *left);
extern BTNode *addsub_expr();
extern BTNode *addsub_expr_tail(BTNode *left);
extern BTNode *muldiv_expr();
extern BTNode *muldiv_expr_tail(BTNode *left);
extern BTNode *unary_expr();
extern void statement(void);

// Print error message and exit the program
extern void err(ErrorType errorNum);

// Test if a token matches the current token
extern int match(TokenSet token);

// Get the next token
extern void advance(void);

// Get the lexeme of the current token
extern char *getLexeme(void);
int regid = 0;

int evaluateTree(BTNode *root) {
    int retval = 0, lv = 0, rv = 0;

    if (root != NULL) {
        switch (root->data) {
        case ID:
            retval = regid++;
            printf("MOV r%d [%d]\n", retval, 4 * getval(root->lexeme));
            break;
        case INT:
            retval = regid++;
            printf("MOV r%d %d\n", retval, atoi(root->lexeme));
            break;
        case ASSIGN:
            if (root->left->data != ID) {
                error(SYNTAXERR);
            }
            rv = evaluateTree(root->right);
            retval = lv;
            printf("MOV [%d] r%d\n", 4 * getval(root->left->lexeme), rv);
            break;
        case ADDSUB:
            lv = evaluateTree(root->left);
            rv = evaluateTree(root->right);
            if (strcmp(root->lexeme, "+") == 0) {
                retval = lv;
                printf("ADD r%d r%d\n", retval, rv);
            } else if (strcmp(root->lexeme, "-") == 0) {
                retval = lv;
                printf("SUB r%d r%d\n", retval, rv);
            }
            regid--;
            break;
        case MULDIV:
            lv = evaluateTree(root->left);
            rv = evaluateTree(root->right);
            if (strcmp(root->lexeme, "*") == 0) {
                retval = lv;
                printf("MUL r%d r%d\n", lv, rv);
            } else if (strcmp(root->lexeme, "/") == 0) {
                if (rv == 0) {
                    error(DIVZERO);
                }
                retval = lv;
                printf("DIV r%d r%d\n", lv, rv);
            }
            regid--;
            break;
        case INCDEC:
            rv = evaluateTree(root->right);
            if (!strcmp(root->lexeme, "++")) {
                retval = rv;
                printf("MOV r%d 1\n", regid + 1);
                printf("ADD r%d r%d\n", rv, regid + 1);
                printf("MOV [%d] r%d\n", 4 * getval(root->right->lexeme), rv);
            } else {
                retval = rv;
                printf("MOV r%d 1\n", regid + 1);
                printf("SUB r%d r%d\n", rv, regid + 1);
                printf("MOV [%d] r%d\n", 4 * getval(root->right->lexeme), rv);
            }
            break;
        case AND:
            lv = evaluateTree(root->left);
            rv = evaluateTree(root->right);
            retval = lv;
            printf("AND r%d r%d\n", lv, rv);
            break;
        case OR:
            lv = evaluateTree(root->left);
            rv = evaluateTree(root->right);
            retval = lv;
            printf("OR r%d r%d\n", lv, rv);
            break;
        case XOR:
            lv = evaluateTree(root->left);
            rv = evaluateTree(root->right);
            retval = lv;
            printf("XOR r%d r%d\n", lv, rv);
            break;
        default:
            retval = 0;
        }
    }
    return retval;
}

void printPrefix(BTNode *root) {
    if (root != NULL) {
        printf("%s ", root->lexeme);
        printPrefix(root->left);
        printPrefix(root->right);
    }
}
#include <ctype.h>
#include <stdio.h>
#include <string.h>

static TokenSet getToken(void);
static TokenSet curToken = UNKNOWN;
static char lexeme[MAXLEN];

TokenSet getToken(void) {
    int i = 0;
    char c = '\0';

    while ((c = fgetc(stdin)) == ' ' || c == '\t')
        ;

    if (isdigit(c)) {
        lexeme[0] = c;
        c = fgetc(stdin);
        i = 1;
        while (isdigit(c) && i < MAXLEN) {
            lexeme[i] = c;
            ++i;
            c = fgetc(stdin);
        }
        ungetc(c, stdin);
        lexeme[i] = '\0';
        return INT;
    } else if (c == '+' || c == '-') {
        lexeme[0] = c;
        c = fgetc(stdin);
        if (c == '+' || c == '-' && c == lexeme[0]) {
            lexeme[1] = c;
            lexeme[2] = '\0';
            return INCDEC;
        } else {
            ungetc(c, stdin);
            lexeme[1] = '\0';
            return ADDSUB;
        }
    } else if (c == '*' || c == '/') {
        lexeme[0] = c;
        lexeme[1] = '\0';
        return MULDIV;
    } else if (c == '\n') {
        lexeme[0] = '\0';
        return END;
    } else if (c == '=') {
        strcpy(lexeme, "=");
        return ASSIGN;
    } else if (c == '(') {
        strcpy(lexeme, "(");
        return LPAREN;
    } else if (c == ')') {
        strcpy(lexeme, ")");
        return RPAREN;
    } else if (isalpha(c)) {
        lexeme[0] = c;
        c = fgetc(stdin);
        i = 1;
        while (isdigit(c) || isalpha(c) || c == '_' && i < MAXLEN) {
            lexeme[i] = c;
            ++i;
            c = fgetc(stdin);
        }
        ungetc(c, stdin);
        lexeme[i] = '\0';
        return ID;
    } else if (c == '&') {
        strcpy(lexeme, "&");
        return AND;
    } else if (c == '|') {
        strcpy(lexeme, "|");
        return OR;
    } else if (c == '^') {
        strcpy(lexeme, "^");
        return XOR;
    } else if (c == EOF) {
        return ENDFILE;
    } else {
        return UNKNOWN;
    }
}

void advance(void) {
    curToken = getToken();
}

int match(TokenSet token) {
    if (curToken == UNKNOWN)
        advance();
    return token == curToken;
}

char *getLexeme(void) {
    return lexeme;
}
#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

// This package is a calculator
// It works like a Python interpretor
// Example:
// >> y = 2
// >> z = 2
// >> x = 3 * y + 4 / (2 * z)
// It will print the answer of every line
// You should turn it into an expression compiler
// And print the assembly code according to the input

// This is the grammar used in this package
// You can modify it according to the spec and the slide
// statement  :=  ENDFILE | END | expr END
// expr    	  :=  term expr_tail
// expr_tail  :=  ADDSUB term expr_tail | NiL
// term 	  :=  factor term_tail
// term_tail  :=  MULDIV factor term_tail| NiL
// factor	  :=  INT | ADDSUB INT |
//		   	      ID  | ADDSUB ID  |
//		   	      ID ASSIGN expr |
//		   	      LPAREN expr RPAREN |
//		   	      ADDSUB LPAREN expr RPAREN
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int sbcount = 0;
Symbol table[TBLSIZE];

void initTable(void) {
    strcpy(table[0].name, "x");
    table[0].val = 0;
    strcpy(table[1].name, "y");
    table[1].val = 0;
    strcpy(table[2].name, "z");
    table[2].val = 0;
    sbcount = 3;
}

int getval(char *str) {
    int i = 0;

    for (i = 0; i < sbcount; i++)
        if (strcmp(str, table[i].name) == 0)
            return i;

    if (sbcount >= TBLSIZE)
        error(RUNOUT);

    strcpy(table[sbcount].name, str);
    table[sbcount].val = 0;
    return sbcount++;
}

int setval(char *str, int val) {
    int i = 0;

    for (i = 0; i < sbcount; i++) {
        if (strcmp(str, table[i].name) == 0) {
            table[i].val = val;
            return val;
        }
    }

    if (sbcount >= TBLSIZE)
        error(RUNOUT);

    strcpy(table[sbcount].name, str);
    table[sbcount].val = val;
    sbcount++;
    return val;
}

BTNode *makeNode(TokenSet tok, const char *lexe) {
    BTNode *node = (BTNode *)malloc(sizeof(BTNode));
    strcpy(node->lexeme, lexe);
    node->data = tok;
    node->val = 0;
    node->left = NULL;
    node->right = NULL;
    return node;
}

void freeTree(BTNode *root) {
    if (root != NULL) {
        freeTree(root->left);
        freeTree(root->right);
        free(root);
    }
}

// factor := INT | ADDSUB INT |
//		   	 ID  | ADDSUB ID  |
//		   	 ID ASSIGN expr |
//		   	 LPAREN expr RPAREN |
//		   	 ADDSUB LPAREN expr RPAREN
BTNode *factor(void) {
    BTNode *retp = NULL, *left = NULL;

    if (match(INT)) {
        retp = makeNode(INT, getLexeme());
        advance();
    } else if (match(ID)) {

        retp = makeNode(ID, getLexeme());
        advance();
    } else if (match(INCDEC)) {
        retp = makeNode(INCDEC, getLexeme());
        advance();
        retp->left = makeNode(INCDEC, "0");
        if (match(ID)) {
            retp->right = makeNode(ID, getLexeme());
            advance();
            return retp;
        } else {
            err(NOTNUMID);
        }
    } else if (match(LPAREN)) {
        advance();
        retp = assign_expr();
        if (match(RPAREN))
            advance();
        else
            error(MISPAREN);
    } else {
        error(NOTNUMID);
    }
    return retp;
}
BTNode *assign_expr() {
    int flag = match(ID);
    BTNode *retp = NULL, *left = NULL;
    left = or_expr();
    if (match(ASSIGN)) {
        if (flag) {
            retp = makeNode(ASSIGN, getLexeme());
            advance();
            retp->left = left;
            retp->right = assign_expr();
            return retp;
        } else {
            err(SYNTAXERR);
        }

    } else {
        return left;
    }
}
BTNode *or_expr() {
    BTNode *retp = xor_expr();
    return or_expr_tail(retp);
}
BTNode *or_expr_tail(BTNode *left) {
    BTNode *retp = NULL;
    if (match(OR)) {
        retp = makeNode(OR, getLexeme());
        retp->left = left;
        advance();
        retp->right = xor_expr();
        return or_expr_tail(retp);
    } else {
        return left;
    }
}
BTNode *xor_expr() {
    BTNode *retp = and_expr();
    return xor_expr_tail(retp);
}
BTNode *xor_expr_tail(BTNode *left) {
    BTNode *retp = NULL;
    if (match(XOR)) {
        retp = makeNode(XOR, getLexeme());
        retp->left = left;
        advance();
        retp->right = and_expr();
        return xor_expr_tail(retp);
    } else {
        return left;
    }
}
BTNode *and_expr() {
    BTNode *retp = addsub_expr();
    return and_expr_tail(retp);
}
BTNode *and_expr_tail(BTNode *left) {
    BTNode *retp = NULL;
    if (match(AND)) {
        retp = makeNode(AND, getLexeme());
        retp->left = left;
        advance();
        retp->right = addsub_expr();
        return and_expr_tail(retp);
    } else {
        return left;
    }
}
BTNode *addsub_expr() {
    BTNode *retp = muldiv_expr();
    return addsub_expr_tail(retp);
}
BTNode *addsub_expr_tail(BTNode *left) {
    BTNode *retp = NULL;
    if (match(ADDSUB)) {
        retp = makeNode(ADDSUB, getLexeme());
        retp->left = left;
        advance();
        retp->right = muldiv_expr();
        return addsub_expr_tail(retp);
    } else {
        return left;
    }
}
BTNode *muldiv_expr() {
    BTNode *retp = unary_expr();
    return muldiv_expr_tail(retp);
}
BTNode *muldiv_expr_tail(BTNode *left) {
    BTNode *retp = NULL;
    if (match(MULDIV)) {
        retp = makeNode(MULDIV, getLexeme());
        retp->left = left;
        advance();
        retp->right = unary_expr();
        return muldiv_expr_tail(retp);
    } else {
        return left;
    }
}
BTNode *unary_expr() {
    BTNode *retp = NULL;
    if (match(ADDSUB)) {
        retp = makeNode(ADDSUB, getLexeme());
        advance();
        retp->left = makeNode(INT, "0");
        retp->right = unary_expr();
    } else {
        retp = factor();
    }
    return retp;
}
// term := factor term_tail
BTNode *term(void) {
    BTNode *node = factor();
    return term_tail(node);
}

// term_tail := MULDIV factor term_tail | NiL
BTNode *term_tail(BTNode *left) {
    BTNode *node = NULL;

    if (match(MULDIV)) {
        node = makeNode(MULDIV, getLexeme());
        advance();
        node->left = left;
        node->right = factor();
        return term_tail(node);
    } else {
        return left;
    }
}

// expr := term expr_tail
BTNode *expr(void) {
    BTNode *node = term();
    return expr_tail(node);
}

// expr_tail := ADDSUB term expr_tail | NiL
BTNode *expr_tail(BTNode *left) {
    BTNode *node = NULL;

    if (match(ADDSUB)) {
        node = makeNode(ADDSUB, getLexeme());
        advance();
        node->left = left;
        node->right = term();
        return expr_tail(node);
    } else {
        return left;
    }
}

// statement := ENDFILE | END | expr END
void statement(void) {
    BTNode *retp = NULL;
    if (match(ENDFILE)) {
        for (int i = 0; i < 3; i++) {
            printf("MOV r%d [%d]\n", i, 4 * i);
        }
        printf("EXIT 0");
        exit(0);
    } else if (match(END)) {
        advance();
    } else {
        regid = 0;
        retp = assign_expr();
        if (match(END)) {
            evaluateTree(retp);
            freeTree(retp);
            advance();
        } else {
            error(SYNTAXERR);
        }
    }
}

void err(ErrorType errorNum) {
    if (PRINTERR) {
        fprintf(stderr, "error: ");
        switch (errorNum) {
        case MISPAREN:
            fprintf(stderr, "mismatched parenthesis\n");
            break;
        case NOTNUMID:
            fprintf(stderr, "number or identifier expected\n");
            break;
        case NOTFOUND:
            fprintf(stderr, "variable not defined\n");
            break;
        case RUNOUT:
            fprintf(stderr, "out of memory\n");
            break;
        case NOTLVAL:
            fprintf(stderr, "lvalue required as an operand\n");
            break;
        case DIVZERO:
            fprintf(stderr, "divide by constant zero\n");
            break;
        case SYNTAXERR:
            fprintf(stderr, "syntax error\n");
            break;
        default:
            fprintf(stderr, "undefined error\n");
            break;
        }
    }
    printf("EXIT 1");
    exit(0);
}

int main() {
    initTable();
    while (1) {
        statement();
    }
    return 0;
}

Raw Text