Esempio n. 1
0
/**
 * "switch" statement
 */
void doswitch(void) {
        WHILE ws;
        WHILE *ptr;

        ws.symbol_idx = local_table_index;
        ws.stack_pointer = stkp;
        ws.type = WSSWITCH;
        ws.case_test = swstp;
        ws.body_tab = getlabel ();
        ws.incr_def = ws.while_exit = getlabel ();
        addwhile (&ws);
        gen_immediate ();
        print_label (ws.body_tab);
        newline ();
        gen_push (HL_REG);
        needbrack ("(");
        expression (YES);
        needbrack (")");
        stkp = stkp + INTSIZE;  // '?case' will adjust the stack
        gen_jump_case ();
        statement (NO);
        ptr = readswitch ();
        gen_jump (ptr->while_exit);
        dumpsw (ptr);
        generate_label (ptr->while_exit);
        local_table_index = ptr->symbol_idx;
        stkp = gen_modify_stack (ptr->stack_pointer);
        swstp = ptr->case_test;
        delwhile ();
}
Esempio n. 2
0
/**
 * "switch" statement
 */
doswitch() {
        loop_t loop;
        loop_t *ptr;

        loop.symbol_idx = local_table_index;
        loop.stack_pointer = stkp;
        loop.type = WSSWITCH;
        loop.test_label = swstp;
        loop.body_label = getlabel ();
        loop.cont_label = loop.exit_label = getlabel ();
        addloop (&loop);
        gen_immediate_a ();
        print_label (loop.body_label);
        newline ();
        gen_push ();
        needbrack ("(");
        expression (YES);
        needbrack (")");
        stkp = stkp + INTSIZE;  // '?case' will adjust the stack
        gen_jump_case ();
        statement (NO);
        ptr = readswitch ();
        gen_jump (ptr->exit_label);
        dumpsw (ptr);
        generate_label (ptr->exit_label);
        local_table_index = ptr->symbol_idx;
        stkp = gen_modify_stack (ptr->stack_pointer);
        swstp = ptr->test_label;
        delloop ();
}
Esempio n. 3
0
/**
 * perform a function call
 * called from "hier11", this routine will either call the named
 * function, or if the supplied ptr is zero, will call the contents
 * of HL
 * @param ptr name of the function
 */
void callfunction(char *ptr) {
    int     nargs;

    nargs = 0;
    blanks ();
    if (ptr == 0)
        gen_push (HL_REG);
    while (!streq (line + lptr, ")")) {
        if (endst ())
            break;
        expression (NO);
        if (ptr == 0)
            gen_swap_stack ();
        gen_push (HL_REG);
        nargs = nargs + INTSIZE;
        if (!match (","))
            break;
    }
    needbrack (")");
    if (aflag)
        gnargs(nargs / INTSIZE);
    if (ptr)
        gen_call (ptr);
    else
        callstk ();
    stkp = gen_modify_stack (stkp + nargs);
}
Esempio n. 4
0
/**
 * "break" statement
 */
dobreak() {
        loop_t *ptr;

        if ((ptr = readloop ()) == 0)
                return;
        gen_modify_stack (ptr->stack_pointer);
        gen_jump (ptr->exit_label);
}
Esempio n. 5
0
/**
 * "break" statement
 */
void dobreak(void) {
        WHILE *ptr;

        if ((ptr = readwhile ()) == 0)
                return;
        gen_modify_stack (ptr->stack_pointer);
        gen_jump (ptr->while_exit);
}
Esempio n. 6
0
/**
 * "continue" statement
 */
void docont(void) {
        WHILE *ptr; //int     *ptr;

        if ((ptr = findwhile ()) == 0)
                return;
        gen_modify_stack (ptr->stack_pointer);
        if (ptr->type == WSFOR)
                gen_jump (ptr->incr_def);
        else
                gen_jump (ptr->case_test);
}
Esempio n. 7
0
/**
 * "continue" statement
 */
docont() {
        loop_t *ptr;

        if ((ptr = findloop ()) == 0)
                return;
        gen_modify_stack (ptr->stack_pointer);
        if (ptr->type == WSFOR)
                gen_jump (ptr->cont_label);
        else
                gen_jump (ptr->test_label);
}
Esempio n. 8
0
/**
 * "if" statement
 */
void doif(void) {
        int     fstkp, flab1, flab2;
        int     flev;

        flev = local_table_index;
        fstkp = stkp;
        flab1 = getlabel ();
        test (flab1, FALSE);
        statement (NO);
        stkp = gen_modify_stack (fstkp);
        local_table_index = flev;
        if (!amatch ("else", 4)) {
                generate_label (flab1);
                return;
        }
        gen_jump (flab2 = getlabel ());
        generate_label (flab1);
        statement (NO);
        stkp = gen_modify_stack (fstkp);
        local_table_index = flev;
        generate_label (flab2);
}
Esempio n. 9
0
/**
 * "while" statement
 */
dowhile() {
        loop_t loop;

        loop.symbol_idx = local_table_index;
        loop.stack_pointer = stkp;
        loop.type = WSWHILE;
        loop.test_label = getlabel ();
        loop.exit_label = getlabel ();
        addloop (&loop);
        generate_label (loop.test_label);
        test (loop.exit_label, FALSE);
        statement (NO);
        gen_jump (loop.test_label);
        generate_label (loop.exit_label);
        local_table_index = loop.symbol_idx;
        stkp = gen_modify_stack (loop.stack_pointer);
        delloop ();
}
Esempio n. 10
0
/**
 * "while" statement
 */
void dowhile(void) {
        WHILE ws;

        ws.symbol_idx = local_table_index;
        ws.stack_pointer = stkp;
        ws.type = WSWHILE;
        ws.case_test = getlabel ();
        ws.while_exit = getlabel ();
        addwhile (&ws);
        generate_label (ws.case_test);
        test (ws.while_exit, FALSE);
        statement (NO);
        gen_jump (ws.case_test);
        generate_label (ws.while_exit);
        local_table_index = ws.symbol_idx;
        stkp = gen_modify_stack (ws.stack_pointer);
        delwhile ();
}
Esempio n. 11
0
/**
 * "for" statement
 */
void dofor(void) {
        WHILE ws;
        WHILE *pws;

        ws.symbol_idx = local_table_index;
        ws.stack_pointer = stkp;
        ws.type = WSFOR;
        ws.case_test = getlabel ();
        ws.incr_def = getlabel ();
        ws.body_tab = getlabel ();
        ws.while_exit = getlabel ();
        addwhile (&ws);
        pws = readwhile ();
        needbrack ("(");
        if (!match (";")) {
                expression (YES);
                need_semicolon ();
        }
        generate_label (pws->case_test);
        if (!match (";")) {
                expression (YES);
                gen_test_jump (pws->body_tab, TRUE);
                gen_jump (pws->while_exit);
                need_semicolon ();
        } else
                pws->case_test = pws->body_tab;
        generate_label (pws->incr_def);
        if (!match (")")) {
                expression (YES);
                needbrack (")");
                gen_jump (pws->case_test);
        } else
                pws->incr_def = pws->case_test;
        generate_label (pws->body_tab);
        statement (NO);
        gen_jump (pws->incr_def);
        generate_label (pws->while_exit);
        local_table_index = pws->symbol_idx;
        stkp = gen_modify_stack (pws->stack_pointer);
        delwhile ();
}
Esempio n. 12
0
/**
 * "for" statement
 */
dofor() {
        loop_t loop;
        loop_t *p;

        loop.symbol_idx = local_table_index;
        loop.stack_pointer = stkp;
        loop.type = WSFOR;
        loop.test_label = getlabel ();
        loop.cont_label = getlabel ();
        loop.body_label = getlabel ();
        loop.exit_label = getlabel ();
        addloop (&loop);
        p = readloop ();
        needbrack ("(");
        if (!match (";")) {
                expression (YES);
                need_semicolon ();
        }
        generate_label (p->test_label);
        if (!match (";")) {
                expression (YES);
                gen_test_jump (p->body_label, TRUE);
                gen_jump (p->exit_label);
                need_semicolon ();
        } else
                p->test_label = p->body_label;
        generate_label (p->cont_label);
        if (!match (")")) {
                expression (YES);
                needbrack (")");
                gen_jump (p->test_label);
        } else
                p->cont_label = p->test_label;
        generate_label (p->body_label);
        statement (NO);
        gen_jump (p->cont_label);
        generate_label (p->exit_label);
        local_table_index = p->symbol_idx;
        stkp = gen_modify_stack (p->stack_pointer);
        delloop ();
}
Esempio n. 13
0
/**
 * "do" statement
 */
dodo() {
        loop_t loop;

        loop.symbol_idx = local_table_index;
        loop.stack_pointer = stkp;
        loop.type = WSDO;
        loop.body_label = getlabel ();
        loop.test_label = getlabel ();
        loop.exit_label = getlabel ();
        addloop (&loop);
        generate_label (loop.body_label);
        statement (NO);
        if (!match ("while")) {
                error ("missing while");
                return;
        }
        generate_label (loop.test_label);
        test (loop.body_label, TRUE);
        generate_label (loop.exit_label);
        local_table_index = loop.symbol_idx;
        stkp = gen_modify_stack (loop.stack_pointer);
        delloop ();
}
Esempio n. 14
0
/**
 * "do" statement
 */
void dodo(void) {
        WHILE ws;

        ws.symbol_idx = local_table_index;
        ws.stack_pointer = stkp;
        ws.type = WSDO;
        ws.body_tab = getlabel ();
        ws.case_test = getlabel ();
        ws.while_exit = getlabel ();
        addwhile (&ws);
        generate_label (ws.body_tab);
        statement (NO);
        if (!match ("while")) {
                error ("missing while");
                return;
        }
        generate_label (ws.case_test);
        test (ws.body_tab, TRUE);
        generate_label (ws.while_exit);
        local_table_index = ws.symbol_idx;
        stkp = gen_modify_stack (ws.stack_pointer);
        delwhile ();
}
Esempio n. 15
0
/**
 * declare local variables
 * works just like "declglb", but modifies machine stack and adds
 * symbol table entry with appropriate stack offset to find it again
 * @param typ
 * @param stclass
 * @param otag index of tag in tag_table
 */
void declare_local(int typ, int stclass, int otag) {
    int     k, j;
    char    sname[NAMESIZE];

    FOREVER {
        FOREVER {
            if (endst())
                return;
            if (match("*"))
                j = POINTER;
            else
                j = VARIABLE;
            if (!symname(sname))
                illname();
            if (-1 != find_locale(sname))
                multidef (sname);
            if (match("[")) {
                k = needsub();
                if (k) {
                    j = ARRAY;
                    if (typ & CINT) {
                        k = k * INTSIZE;
                    } else if (typ == STRUCT) {
                        k = k * tag_table[otag].size;
                    }
                } else {
                    j = POINTER;
                    k = INTSIZE;
                }
            } else {
                if (j == POINTER) {
                    k = INTSIZE;
                } else {
                    switch (typ) {
                        case CCHAR:
                        case UCHAR:
                            k = 1;
                            break;
                        case STRUCT:
                            k = tag_table[otag].size;
                            break;
                        default:
                            k = INTSIZE;
                    }
                }
            }
            if (stclass == LSTATIC) {
                add_local(sname, j, typ, k, LSTATIC);
                break;
            }
            if (stclass == REGISTER) {
                int r = gen_register(j, k, typ);
                if (r != -1) {
                    add_local(sname, j, typ, r, REGISTER);
                    break;
                }
            }
            if (match("=")) {
                gen_modify_stack(stkp);
                expression(0);
                gen_push(0);
            } else
                stkp = gen_defer_modify_stack(stkp - k);
            add_local(sname, j, typ, stkp, AUTO);
            break;
        }
        if (!match(","))
            return;
    }
}
Esempio n. 16
0
void newfunc_typed(int storage, char *n, int type)
{
    int idx;
    SYMBOL *symbol;
    char an[NAMESIZE];

    fexitlab = getlabel();

    if ((idx = find_global(n)) > -1) {
        symbol = &symbol_table[idx];
        if (symbol->identity != FUNCTION)
            multidef(n);
    } else {
        /* extern implies global scope */
        idx = add_global(n, FUNCTION, CINT, 0, storage == EXTERN ? PUBLIC : storage);
        symbol = &symbol_table[idx];
    }
    local_table_index = NUMBER_OF_GLOBALS; //locptr = STARTLOC;
    argstk = 0;
    // ANSI style argument declaration
    if (doAnsiArguments()) {
        if (storage == EXTERN) {
            need_semicolon();
            return;
        }
        /* No body .. just a definition */
        if (match(";"))
            return;
    } else {
        // K&R style argument declaration
        while (!match(")")) {
            if (symname(an)) {
                if (find_locale(an) > -1)
                    multidef(an);
                else {
                    /* FIXME: struct */
                    add_local(an, 0, 0, argstk, AUTO);
                    argstk = argstk + INTSIZE;
                }
            } else {
                error("illegal argument name");
                junk();
            }
            blanks();
            if (!streq(line + lptr, ")")) {
                if (!match(","))
                    error("expected comma");
            }
            if (endst())
                break;
        }
        if (storage == EXTERN) {
            need_semicolon();
            return;
        }
        /* No body .. just a definition */
        if (match(";"))
            return;
        stkp = 0;
        argtop = argstk;
        while (argstk) {
            if ((type = get_type()) != -1) {
                notvoid(type);
                getarg(type);
                need_semicolon();
            } else {
                error("wrong number args");
                break;
            }
        }
    }
    if (symbol->offset == FUNCTION)
            multidef(n);
    symbol->offset = FUNCTION;
    output_string(n);
    output_label_terminator();
    newline();
    gen_prologue();
    statement(YES);
    print_label(fexitlab);
    output_label_terminator();
    newline();
    gen_epilogue();
    gen_modify_stack(0);
    gen_ret();
    stkp = 0;
    local_table_index = NUMBER_OF_GLOBALS; //locptr = STARTLOC;
}
Esempio n. 17
0
/**
 * begin a function
 * called from "parse", this routine tries to make a function out
 * of what follows
 * modified version.  p.l. woods
 */
newfunc() {
    char n[NAMESIZE];
    int idx, type;
    fexitlab = getlabel();

    if (!symname(n)) {
        error("illegal function or declaration");
        kill();
        return;
    }
    if (idx = findglb(n)) {
        if (symbol_table[idx].identity != FUNCTION)
            multidef(n);
        else if (symbol_table[idx].offset == FUNCTION)
            multidef(n);
        else
            symbol_table[idx].offset = FUNCTION;
    } else
        add_global(n, FUNCTION, CINT, FUNCTION, PUBLIC);
    if (!match("("))
        error("missing open paren");
    output_string(n);
    output_label_terminator();
    newline();
    local_table_index = NUMBER_OF_GLOBALS; //locptr = STARTLOC;
    argstk = 0;
    // ANSI style argument declaration
    if (doAnsiArguments() == 0) {
        // K&R style argument declaration
        while (!match(")")) {
            if (symname(n)) {
                if (findloc(n))
                    multidef(n);
                else {
                    add_local(n, 0, 0, argstk, AUTO);
                    argstk = argstk + INTSIZE;
                }
            } else {
                error("illegal argument name");
                junk();
            }
            blanks();
            if (!streq(line + lptr, ")")) {
                if (!match(","))
                    error("expected comma");
            }
            if (endst())
                break;
        }
        stkp = 0;
        argtop = argstk;
        while (argstk) {
            if (type = get_type()) {
                getarg(type);
                need_semicolon();
            } else {
                error("wrong number args");
                break;
            }
        }
    }
    statement(YES);
    print_label(fexitlab);
    output_label_terminator();
    newline();
    gen_modify_stack(0);
    gen_ret();
    stkp = 0;
    local_table_index = NUMBER_OF_GLOBALS; //locptr = STARTLOC;
}
Esempio n. 18
0
/* FIXME - interaction with register needs thought */
int gen_defer_modify_stack(int newstkp)
{
    return gen_modify_stack(newstkp);
}