OpenCores
URL https://opencores.org/ocsvn/eco32/eco32/trunk

Subversion Repositories eco32

[/] [eco32/] [tags/] [eco32-0.26/] [fp/] [investigate/] [expr.c] - Diff between revs 15 and 270

Only display areas with differences | Details | Blame | View Log

Rev 15 Rev 270
#include "c.h"
#include "c.h"
 
 
static char rcsid[] = "$Id: expr.c,v 1.1 2002/08/28 23:12:43 drh Exp $";
static char rcsid[] = "$Id: expr.c,v 1.1 2002/08/28 23:12:43 drh Exp $";
 
 
static char prec[] = {
static char prec[] = {
#define xx(a,b,c,d,e,f,g) c,
#define xx(a,b,c,d,e,f,g) c,
#define yy(a,b,c,d,e,f,g) c,
#define yy(a,b,c,d,e,f,g) c,
#include "token.h"
#include "token.h"
};
};
static int oper[] = {
static int oper[] = {
#define xx(a,b,c,d,e,f,g) d,
#define xx(a,b,c,d,e,f,g) d,
#define yy(a,b,c,d,e,f,g) d,
#define yy(a,b,c,d,e,f,g) d,
#include "token.h"
#include "token.h"
};
};
float refinc = 1.0;
float refinc = 1.0;
static Tree expr2(void);
static Tree expr2(void);
static Tree expr3(int);
static Tree expr3(int);
static Tree nullcheck(Tree);
static Tree nullcheck(Tree);
static Tree postfix(Tree);
static Tree postfix(Tree);
static Tree unary(void);
static Tree unary(void);
static Tree primary(void);
static Tree primary(void);
static Type super(Type ty);
static Type super(Type ty);
 
 
static Type super(Type ty) {
static Type super(Type ty) {
        switch (ty->op) {
        switch (ty->op) {
        case INT:
        case INT:
                if (ty->size < inttype->size)
                if (ty->size < inttype->size)
                        return inttype;
                        return inttype;
                break;
                break;
        case UNSIGNED:
        case UNSIGNED:
                if (ty->size < unsignedtype->size)
                if (ty->size < unsignedtype->size)
                        return unsignedtype;
                        return unsignedtype;
                break;
                break;
        case POINTER:
        case POINTER:
                return unsignedptr;
                return unsignedptr;
        }
        }
        return ty;
        return ty;
}
}
Tree expr(int tok) {
Tree expr(int tok) {
        static char stop[] = { IF, ID, '}', 0 };
        static char stop[] = { IF, ID, '}', 0 };
        Tree p = expr1(0);
        Tree p = expr1(0);
 
 
        while (t == ',') {
        while (t == ',') {
                Tree q;
                Tree q;
                t = gettok();
                t = gettok();
                q = pointer(expr1(0));
                q = pointer(expr1(0));
                p = tree(RIGHT, q->type, root(value(p)), q);
                p = tree(RIGHT, q->type, root(value(p)), q);
        }
        }
        if (tok)
        if (tok)
                test(tok, stop);
                test(tok, stop);
        return p;
        return p;
}
}
Tree expr0(int tok) {
Tree expr0(int tok) {
        return root(expr(tok));
        return root(expr(tok));
}
}
Tree expr1(int tok) {
Tree expr1(int tok) {
        static char stop[] = { IF, ID, 0 };
        static char stop[] = { IF, ID, 0 };
        Tree p = expr2();
        Tree p = expr2();
 
 
        if (t == '='
        if (t == '='
        || (prec[t] >=  6 && prec[t] <=  8)
        || (prec[t] >=  6 && prec[t] <=  8)
        || (prec[t] >= 11 && prec[t] <= 13)) {
        || (prec[t] >= 11 && prec[t] <= 13)) {
                int op = t;
                int op = t;
                t = gettok();
                t = gettok();
                if (oper[op] == ASGN)
                if (oper[op] == ASGN)
                        p = asgntree(ASGN, p, value(expr1(0)));
                        p = asgntree(ASGN, p, value(expr1(0)));
                else
                else
                        {
                        {
                                expect('=');
                                expect('=');
                                p = incr(op, p, expr1(0));
                                p = incr(op, p, expr1(0));
                        }
                        }
        }
        }
        if (tok)
        if (tok)
                test(tok, stop);
                test(tok, stop);
        return p;
        return p;
}
}
Tree incr(int op, Tree v, Tree e) {
Tree incr(int op, Tree v, Tree e) {
        return asgntree(ASGN, v, (*optree[op])(oper[op], v, e));
        return asgntree(ASGN, v, (*optree[op])(oper[op], v, e));
}
}
static Tree expr2(void) {
static Tree expr2(void) {
        Tree p = expr3(4);
        Tree p = expr3(4);
 
 
        if (t == '?') {
        if (t == '?') {
                Tree l, r;
                Tree l, r;
                Coordinate pts[2];
                Coordinate pts[2];
                if (Aflag > 1 && isfunc(p->type))
                if (Aflag > 1 && isfunc(p->type))
                        warning("%s used in a conditional expression\n",
                        warning("%s used in a conditional expression\n",
                                funcname(p));
                                funcname(p));
                p = pointer(p);
                p = pointer(p);
                t = gettok();
                t = gettok();
                pts[0] = src;
                pts[0] = src;
                l = pointer(expr(':'));
                l = pointer(expr(':'));
                pts[1] = src;
                pts[1] = src;
                r = pointer(expr2());
                r = pointer(expr2());
                if (generic(p->op) != CNST && events.points)
                if (generic(p->op) != CNST && events.points)
                        {
                        {
                                apply(events.points, &pts[0], &l);
                                apply(events.points, &pts[0], &l);
                                apply(events.points, &pts[1], &r);
                                apply(events.points, &pts[1], &r);
                        }
                        }
                p = condtree(p, l, r);
                p = condtree(p, l, r);
        }
        }
        return p;
        return p;
}
}
Tree value(Tree p) {
Tree value(Tree p) {
        int op = generic(rightkid(p)->op);
        int op = generic(rightkid(p)->op);
 
 
        if (p->type != voidtype
        if (p->type != voidtype
        && (op==AND || op==OR || op==NOT || op==EQ || op==NE
        && (op==AND || op==OR || op==NOT || op==EQ || op==NE
        ||  op== LE || op==LT || op== GE || op==GT))
        ||  op== LE || op==LT || op== GE || op==GT))
                p = condtree(p, consttree(1, inttype),
                p = condtree(p, consttree(1, inttype),
                        consttree(0, inttype));
                        consttree(0, inttype));
        return p;
        return p;
}
}
static Tree expr3(int k) {
static Tree expr3(int k) {
        int k1;
        int k1;
        Tree p = unary();
        Tree p = unary();
 
 
        for (k1 = prec[t]; k1 >= k; k1--)
        for (k1 = prec[t]; k1 >= k; k1--)
                while (prec[t] == k1 && *cp != '=') {
                while (prec[t] == k1 && *cp != '=') {
                        Tree r;
                        Tree r;
                        Coordinate pt;
                        Coordinate pt;
                        int op = t;
                        int op = t;
                        t = gettok();
                        t = gettok();
                        pt = src;
                        pt = src;
                        p = pointer(p);
                        p = pointer(p);
                        if (op == ANDAND || op == OROR) {
                        if (op == ANDAND || op == OROR) {
                                r = pointer(expr3(k1));
                                r = pointer(expr3(k1));
                                if (events.points)
                                if (events.points)
                                        apply(events.points, &pt, &r);
                                        apply(events.points, &pt, &r);
                        } else
                        } else
                                r = pointer(expr3(k1 + 1));
                                r = pointer(expr3(k1 + 1));
                        p = (*optree[op])(oper[op], p, r);
                        p = (*optree[op])(oper[op], p, r);
                }
                }
        return p;
        return p;
}
}
static Tree unary(void) {
static Tree unary(void) {
        Tree p;
        Tree p;
 
 
        switch (t) {
        switch (t) {
        case '*':    t = gettok(); p = unary(); p = pointer(p);
        case '*':    t = gettok(); p = unary(); p = pointer(p);
                                                  if (isptr(p->type)
                                                  if (isptr(p->type)
                                                  && (isfunc(p->type->type) || isarray(p->type->type)))
                                                  && (isfunc(p->type->type) || isarray(p->type->type)))
                                                        p = retype(p, p->type->type);
                                                        p = retype(p, p->type->type);
                                                  else {
                                                  else {
                                                        if (YYnull)
                                                        if (YYnull)
                                                                p = nullcheck(p);
                                                                p = nullcheck(p);
                                                        p = rvalue(p);
                                                        p = rvalue(p);
                                                  } break;
                                                  } break;
        case '&':    t = gettok(); p = unary(); if (isarray(p->type) || isfunc(p->type))
        case '&':    t = gettok(); p = unary(); if (isarray(p->type) || isfunc(p->type))
                                                        p = retype(p, ptr(p->type));
                                                        p = retype(p, ptr(p->type));
                                                  else
                                                  else
                                                        p = lvalue(p);
                                                        p = lvalue(p);
                                                  if (isaddrop(p->op) && p->u.sym->sclass == REGISTER)
                                                  if (isaddrop(p->op) && p->u.sym->sclass == REGISTER)
                                                        error("invalid operand of unary &; `%s' is declared register\n", p->u.sym->name);
                                                        error("invalid operand of unary &; `%s' is declared register\n", p->u.sym->name);
 
 
                                                  else if (isaddrop(p->op))
                                                  else if (isaddrop(p->op))
                                                        p->u.sym->addressed = 1;
                                                        p->u.sym->addressed = 1;
 break;
 break;
        case '+':    t = gettok(); p = unary(); p = pointer(p);
        case '+':    t = gettok(); p = unary(); p = pointer(p);
                                                  if (isarith(p->type))
                                                  if (isarith(p->type))
                                                        p = cast(p, promote(p->type));
                                                        p = cast(p, promote(p->type));
                                                  else
                                                  else
                                                        typeerror(ADD, p, NULL);  break;
                                                        typeerror(ADD, p, NULL);  break;
        case '-':    t = gettok(); p = unary(); p = pointer(p);
        case '-':    t = gettok(); p = unary(); p = pointer(p);
                                                  if (isarith(p->type)) {
                                                  if (isarith(p->type)) {
                                                        Type ty = promote(p->type);
                                                        Type ty = promote(p->type);
                                                        p = cast(p, ty);
                                                        p = cast(p, ty);
                                                        if (isunsigned(ty)) {
                                                        if (isunsigned(ty)) {
                                                                warning("unsigned operand of unary -\n");
                                                                warning("unsigned operand of unary -\n");
                                                                p = simplify(ADD, ty, simplify(BCOM, ty, p, NULL), cnsttree(ty, 1UL));
                                                                p = simplify(ADD, ty, simplify(BCOM, ty, p, NULL), cnsttree(ty, 1UL));
                                                        } else
                                                        } else
                                                                p = simplify(NEG, ty, p, NULL);
                                                                p = simplify(NEG, ty, p, NULL);
                                                  } else
                                                  } else
                                                        typeerror(SUB, p, NULL); break;
                                                        typeerror(SUB, p, NULL); break;
        case '~':    t = gettok(); p = unary(); p = pointer(p);
        case '~':    t = gettok(); p = unary(); p = pointer(p);
                                                  if (isint(p->type)) {
                                                  if (isint(p->type)) {
                                                        Type ty = promote(p->type);
                                                        Type ty = promote(p->type);
                                                        p = simplify(BCOM, ty, cast(p, ty), NULL);
                                                        p = simplify(BCOM, ty, cast(p, ty), NULL);
                                                  } else
                                                  } else
                                                        typeerror(BCOM, p, NULL);  break;
                                                        typeerror(BCOM, p, NULL);  break;
        case '!':    t = gettok(); p = unary(); p = pointer(p);
        case '!':    t = gettok(); p = unary(); p = pointer(p);
                                                  if (isscalar(p->type))
                                                  if (isscalar(p->type))
                                                        p = simplify(NOT, inttype, cond(p), NULL);
                                                        p = simplify(NOT, inttype, cond(p), NULL);
                                                  else
                                                  else
                                                        typeerror(NOT, p, NULL); break;
                                                        typeerror(NOT, p, NULL); break;
        case INCR:   t = gettok(); p = unary(); p = incr(INCR, pointer(p), consttree(1, inttype)); break;
        case INCR:   t = gettok(); p = unary(); p = incr(INCR, pointer(p), consttree(1, inttype)); break;
        case DECR:   t = gettok(); p = unary(); p = incr(DECR, pointer(p), consttree(1, inttype)); break;
        case DECR:   t = gettok(); p = unary(); p = incr(DECR, pointer(p), consttree(1, inttype)); break;
        case TYPECODE: case SIZEOF: { int op = t;
        case TYPECODE: case SIZEOF: { int op = t;
                                      Type ty;
                                      Type ty;
                                      p = NULL;
                                      p = NULL;
                                      t = gettok();
                                      t = gettok();
                                      if (t == '(') {
                                      if (t == '(') {
                                        t = gettok();
                                        t = gettok();
                                        if (istypename(t, tsym)) {
                                        if (istypename(t, tsym)) {
                                                ty = typename();
                                                ty = typename();
                                                expect(')');
                                                expect(')');
                                        } else {
                                        } else {
                                                p = postfix(expr(')'));
                                                p = postfix(expr(')'));
                                                ty = p->type;
                                                ty = p->type;
                                        }
                                        }
                                      } else {
                                      } else {
                                        p = unary();
                                        p = unary();
                                        ty = p->type;
                                        ty = p->type;
                                      }
                                      }
                                      assert(ty);
                                      assert(ty);
                                      if (op == TYPECODE)
                                      if (op == TYPECODE)
                                        p = cnsttree(inttype, (long)ty->op);
                                        p = cnsttree(inttype, (long)ty->op);
                                      else {
                                      else {
                                        if (isfunc(ty) || ty->size == 0)
                                        if (isfunc(ty) || ty->size == 0)
                                                error("invalid type argument `%t' to `sizeof'\n", ty);
                                                error("invalid type argument `%t' to `sizeof'\n", ty);
                                        else if (p && rightkid(p)->op == FIELD)
                                        else if (p && rightkid(p)->op == FIELD)
                                                error("`sizeof' applied to a bit field\n");
                                                error("`sizeof' applied to a bit field\n");
                                        p = cnsttree(unsignedlong, (unsigned long)ty->size);
                                        p = cnsttree(unsignedlong, (unsigned long)ty->size);
                                      } } break;
                                      } } break;
        case '(':
        case '(':
                t = gettok();
                t = gettok();
                if (istypename(t, tsym)) {
                if (istypename(t, tsym)) {
                        Type ty, ty1 = typename(), pty;
                        Type ty, ty1 = typename(), pty;
                        expect(')');
                        expect(')');
                        ty = unqual(ty1);
                        ty = unqual(ty1);
                        if (isenum(ty)) {
                        if (isenum(ty)) {
                                Type ty2 = ty->type;
                                Type ty2 = ty->type;
                                if (isconst(ty1))
                                if (isconst(ty1))
                                        ty2 = qual(CONST, ty2);
                                        ty2 = qual(CONST, ty2);
                                if (isvolatile(ty1))
                                if (isvolatile(ty1))
                                        ty2 = qual(VOLATILE, ty2);
                                        ty2 = qual(VOLATILE, ty2);
                                ty1 = ty2;
                                ty1 = ty2;
                                ty = ty->type;
                                ty = ty->type;
                        }
                        }
                        p = pointer(unary());
                        p = pointer(unary());
                        pty = p->type;
                        pty = p->type;
                        if (isenum(pty))
                        if (isenum(pty))
                                pty = pty->type;
                                pty = pty->type;
                        if (isarith(pty) && isarith(ty)
                        if (isarith(pty) && isarith(ty)
                        ||  isptr(pty)   && isptr(ty)) {
                        ||  isptr(pty)   && isptr(ty)) {
                                explicitCast++;
                                explicitCast++;
                                p = cast(p, ty);
                                p = cast(p, ty);
                                explicitCast--;
                                explicitCast--;
                        } else if (isptr(pty) && isint(ty)
                        } else if (isptr(pty) && isint(ty)
                        ||       isint(pty) && isptr(ty)) {
                        ||       isint(pty) && isptr(ty)) {
                                if (Aflag >= 1 && ty->size < pty->size)
                                if (Aflag >= 1 && ty->size < pty->size)
                                        warning("conversion from `%t' to `%t' is compiler dependent\n", p->type, ty);
                                        warning("conversion from `%t' to `%t' is compiler dependent\n", p->type, ty);
 
 
                                p = cast(p, ty);
                                p = cast(p, ty);
                        } else if (ty != voidtype) {
                        } else if (ty != voidtype) {
                                error("cast from `%t' to `%t' is illegal\n",
                                error("cast from `%t' to `%t' is illegal\n",
                                        p->type, ty1);
                                        p->type, ty1);
                                ty1 = inttype;
                                ty1 = inttype;
                        }
                        }
                        if (generic(p->op) == INDIR || ty->size == 0)
                        if (generic(p->op) == INDIR || ty->size == 0)
                                p = tree(RIGHT, ty1, NULL, p);
                                p = tree(RIGHT, ty1, NULL, p);
                        else
                        else
                                p = retype(p, ty1);
                                p = retype(p, ty1);
                } else
                } else
                        p = postfix(expr(')'));
                        p = postfix(expr(')'));
                break;
                break;
        default:
        default:
                p = postfix(primary());
                p = postfix(primary());
        }
        }
        return p;
        return p;
}
}
 
 
static Tree postfix(Tree p) {
static Tree postfix(Tree p) {
        for (;;)
        for (;;)
                switch (t) {
                switch (t) {
                case INCR:  p = tree(RIGHT, p->type,
                case INCR:  p = tree(RIGHT, p->type,
                                tree(RIGHT, p->type,
                                tree(RIGHT, p->type,
                                        p,
                                        p,
                                        incr(t, p, consttree(1, inttype))),
                                        incr(t, p, consttree(1, inttype))),
                                p);
                                p);
                            t = gettok(); break;
                            t = gettok(); break;
                case DECR:  p = tree(RIGHT, p->type,
                case DECR:  p = tree(RIGHT, p->type,
                                tree(RIGHT, p->type,
                                tree(RIGHT, p->type,
                                        p,
                                        p,
                                        incr(t, p, consttree(1, inttype))),
                                        incr(t, p, consttree(1, inttype))),
                                p);
                                p);
                            t = gettok(); break;
                            t = gettok(); break;
                case '[':   {
                case '[':   {
                                Tree q;
                                Tree q;
                                t = gettok();
                                t = gettok();
                                q = expr(']');
                                q = expr(']');
                                if (YYnull)
                                if (YYnull)
                                        if (isptr(p->type))
                                        if (isptr(p->type))
                                                p = nullcheck(p);
                                                p = nullcheck(p);
                                        else if (isptr(q->type))
                                        else if (isptr(q->type))
                                                q = nullcheck(q);
                                                q = nullcheck(q);
                                p = (*optree['+'])(ADD, pointer(p), pointer(q));
                                p = (*optree['+'])(ADD, pointer(p), pointer(q));
                                if (isptr(p->type) && isarray(p->type->type))
                                if (isptr(p->type) && isarray(p->type->type))
                                        p = retype(p, p->type->type);
                                        p = retype(p, p->type->type);
                                else
                                else
                                        p = rvalue(p);
                                        p = rvalue(p);
                            } break;
                            } break;
                case '(':   {
                case '(':   {
                                Type ty;
                                Type ty;
                                Coordinate pt;
                                Coordinate pt;
                                p = pointer(p);
                                p = pointer(p);
                                if (isptr(p->type) && isfunc(p->type->type))
                                if (isptr(p->type) && isfunc(p->type->type))
                                        ty = p->type->type;
                                        ty = p->type->type;
                                else {
                                else {
                                        error("found `%t' expected a function\n", p->type);
                                        error("found `%t' expected a function\n", p->type);
                                        ty = func(voidtype, NULL, 1);
                                        ty = func(voidtype, NULL, 1);
                                        p = retype(p, ptr(ty));
                                        p = retype(p, ptr(ty));
                                }
                                }
                                pt = src;
                                pt = src;
                                t = gettok();
                                t = gettok();
                                p = call(p, ty, pt);
                                p = call(p, ty, pt);
                            } break;
                            } break;
                case '.':   t = gettok();
                case '.':   t = gettok();
                            if (t == ID) {
                            if (t == ID) {
                                if (isstruct(p->type)) {
                                if (isstruct(p->type)) {
                                        Tree q = addrof(p);
                                        Tree q = addrof(p);
                                        p = field(q, token);
                                        p = field(q, token);
                                        q = rightkid(q);
                                        q = rightkid(q);
                                        if (isaddrop(q->op) && q->u.sym->temporary)
                                        if (isaddrop(q->op) && q->u.sym->temporary)
                                                p = tree(RIGHT, p->type, p, NULL);
                                                p = tree(RIGHT, p->type, p, NULL);
                                } else
                                } else
                                        error("left operand of . has incompatible type `%t'\n",
                                        error("left operand of . has incompatible type `%t'\n",
                                                p->type);
                                                p->type);
                                t = gettok();
                                t = gettok();
                            } else
                            } else
                                error("field name expected\n"); break;
                                error("field name expected\n"); break;
                case DEREF: t = gettok();
                case DEREF: t = gettok();
                            p = pointer(p);
                            p = pointer(p);
                            if (t == ID) {
                            if (t == ID) {
                                if (isptr(p->type) && isstruct(p->type->type)) {
                                if (isptr(p->type) && isstruct(p->type->type)) {
                                        if (YYnull)
                                        if (YYnull)
                                                p = nullcheck(p);
                                                p = nullcheck(p);
                                        p = field(p, token);
                                        p = field(p, token);
                                } else
                                } else
                                        error("left operand of -> has incompatible type `%t'\n", p->type);
                                        error("left operand of -> has incompatible type `%t'\n", p->type);
 
 
                                t = gettok();
                                t = gettok();
                            } else
                            } else
                                error("field name expected\n"); break;
                                error("field name expected\n"); break;
                default:
                default:
                        return p;
                        return p;
                }
                }
}
}
static Tree primary(void) {
static Tree primary(void) {
        Tree p;
        Tree p;
 
 
        assert(t != '(');
        assert(t != '(');
        switch (t) {
        switch (t) {
        case ICON:
        case ICON:
        case FCON: p = tree(mkop(CNST,tsym->type), tsym->type, NULL, NULL);
        case FCON: p = tree(mkop(CNST,tsym->type), tsym->type, NULL, NULL);
                   p->u.v = tsym->u.c.v;
                   p->u.v = tsym->u.c.v;
 break;
 break;
        case SCON: if (ischar(tsym->type->type))
        case SCON: if (ischar(tsym->type->type))
                        tsym->u.c.v.p = stringn(tsym->u.c.v.p, tsym->type->size);
                        tsym->u.c.v.p = stringn(tsym->u.c.v.p, tsym->type->size);
                   else
                   else
                        tsym->u.c.v.p = memcpy(allocate((tsym->type->size/widechar->size)*sizeof (int), PERM),
                        tsym->u.c.v.p = memcpy(allocate((tsym->type->size/widechar->size)*sizeof (int), PERM),
                                tsym->u.c.v.p, (tsym->type->size/widechar->size)*sizeof (int));
                                tsym->u.c.v.p, (tsym->type->size/widechar->size)*sizeof (int));
                   tsym = constant(tsym->type, tsym->u.c.v);
                   tsym = constant(tsym->type, tsym->u.c.v);
                   if (tsym->u.c.loc == NULL)
                   if (tsym->u.c.loc == NULL)
                        tsym->u.c.loc = genident(STATIC, tsym->type, GLOBAL);
                        tsym->u.c.loc = genident(STATIC, tsym->type, GLOBAL);
                   p = idtree(tsym->u.c.loc); break;
                   p = idtree(tsym->u.c.loc); break;
        case ID:   if (tsym == NULL)
        case ID:   if (tsym == NULL)
                        {
                        {
                                Symbol p = install(token, &identifiers, level, PERM);
                                Symbol p = install(token, &identifiers, level, PERM);
                                p->src = src;
                                p->src = src;
                                if (getchr() == '(') {
                                if (getchr() == '(') {
                                        Symbol q = lookup(token, externals);
                                        Symbol q = lookup(token, externals);
                                        p->type = func(inttype, NULL, 1);
                                        p->type = func(inttype, NULL, 1);
                                        p->sclass = EXTERN;
                                        p->sclass = EXTERN;
                                        if (Aflag >= 1)
                                        if (Aflag >= 1)
                                                warning("missing prototype\n");
                                                warning("missing prototype\n");
                                        if (q && !eqtype(q->type, p->type, 1))
                                        if (q && !eqtype(q->type, p->type, 1))
                                                warning("implicit declaration of `%s' does not match previous declaration at %w\n", q->name, &q->src);
                                                warning("implicit declaration of `%s' does not match previous declaration at %w\n", q->name, &q->src);
 
 
                                        if (q == NULL) {
                                        if (q == NULL) {
                                                q = install(p->name, &externals, GLOBAL, PERM);
                                                q = install(p->name, &externals, GLOBAL, PERM);
                                                q->type = p->type;
                                                q->type = p->type;
                                                q->sclass = EXTERN;
                                                q->sclass = EXTERN;
                                                q->src = src;
                                                q->src = src;
                                                (*IR->defsymbol)(q);
                                                (*IR->defsymbol)(q);
                                        }
                                        }
                                        p->u.alias = q;
                                        p->u.alias = q;
                                } else {
                                } else {
                                        error("undeclared identifier `%s'\n", p->name);
                                        error("undeclared identifier `%s'\n", p->name);
                                        p->sclass = AUTO;
                                        p->sclass = AUTO;
                                        p->type = inttype;
                                        p->type = inttype;
                                        if (p->scope == GLOBAL)
                                        if (p->scope == GLOBAL)
                                                (*IR->defsymbol)(p);
                                                (*IR->defsymbol)(p);
                                        else
                                        else
                                                addlocal(p);
                                                addlocal(p);
                                }
                                }
                                t = gettok();
                                t = gettok();
                                if (xref)
                                if (xref)
                                        use(p, src);
                                        use(p, src);
                                return idtree(p);
                                return idtree(p);
                        }
                        }
                   if (xref)
                   if (xref)
                        use(tsym, src);
                        use(tsym, src);
                   if (tsym->sclass == ENUM)
                   if (tsym->sclass == ENUM)
                        p = consttree(tsym->u.value, inttype);
                        p = consttree(tsym->u.value, inttype);
                   else {
                   else {
                        if (tsym->sclass == TYPEDEF)
                        if (tsym->sclass == TYPEDEF)
                                error("illegal use of type name `%s'\n", tsym->name);
                                error("illegal use of type name `%s'\n", tsym->name);
                        p = idtree(tsym);
                        p = idtree(tsym);
                   } break;
                   } break;
        case FIRSTARG:
        case FIRSTARG:
                if (level > PARAM && cfunc && cfunc->u.f.callee[0])
                if (level > PARAM && cfunc && cfunc->u.f.callee[0])
                        p = idtree(cfunc->u.f.callee[0]);
                        p = idtree(cfunc->u.f.callee[0]);
                else {
                else {
                        error("illegal use of `%k'\n", FIRSTARG);
                        error("illegal use of `%k'\n", FIRSTARG);
                        p = cnsttree(inttype, 0L);
                        p = cnsttree(inttype, 0L);
                }
                }
                break;
                break;
        default:
        default:
                error("illegal expression\n");
                error("illegal expression\n");
                        p = cnsttree(inttype, 0L);
                        p = cnsttree(inttype, 0L);
        }
        }
        t = gettok();
        t = gettok();
        return p;
        return p;
}
}
Tree idtree(Symbol p) {
Tree idtree(Symbol p) {
        int op;
        int op;
        Tree e;
        Tree e;
        Type ty = p->type ? unqual(p->type) : voidptype;
        Type ty = p->type ? unqual(p->type) : voidptype;
 
 
        if (p->scope == GLOBAL || p->sclass == STATIC)
        if (p->scope == GLOBAL || p->sclass == STATIC)
                op = ADDRG;
                op = ADDRG;
        else if (p->scope == PARAM) {
        else if (p->scope == PARAM) {
                op = ADDRF;
                op = ADDRF;
                if (isstruct(p->type) && !IR->wants_argb)
                if (isstruct(p->type) && !IR->wants_argb)
                        {
                        {
                                e = tree(mkop(op,voidptype), ptr(ptr(p->type)), NULL, NULL);
                                e = tree(mkop(op,voidptype), ptr(ptr(p->type)), NULL, NULL);
                                e->u.sym = p;
                                e->u.sym = p;
                                return rvalue(rvalue(e));
                                return rvalue(rvalue(e));
                        }
                        }
        } else if (p->sclass == EXTERN) {
        } else if (p->sclass == EXTERN) {
                assert(p->u.alias);
                assert(p->u.alias);
                p = p->u.alias;
                p = p->u.alias;
                op = ADDRG;
                op = ADDRG;
        } else
        } else
                op = ADDRL;
                op = ADDRL;
        p->ref += refinc;
        p->ref += refinc;
        if (isarray(ty))
        if (isarray(ty))
                e = tree(mkop(op,voidptype), p->type,      NULL, NULL);
                e = tree(mkop(op,voidptype), p->type,      NULL, NULL);
        else if (isfunc(ty))
        else if (isfunc(ty))
                e = tree(mkop(op,funcptype), p->type,      NULL, NULL);
                e = tree(mkop(op,funcptype), p->type,      NULL, NULL);
        else
        else
                e = tree(mkop(op,voidptype), ptr(p->type), NULL, NULL);
                e = tree(mkop(op,voidptype), ptr(p->type), NULL, NULL);
        e->u.sym = p;
        e->u.sym = p;
        if (isptr(e->type))
        if (isptr(e->type))
                e = rvalue(e);
                e = rvalue(e);
        return e;
        return e;
}
}
 
 
Tree rvalue(Tree p) {
Tree rvalue(Tree p) {
        Type ty = deref(p->type);
        Type ty = deref(p->type);
 
 
        ty = unqual(ty);
        ty = unqual(ty);
        return tree(mkop(INDIR,ty), ty, p, NULL);
        return tree(mkop(INDIR,ty), ty, p, NULL);
}
}
Tree lvalue(Tree p) {
Tree lvalue(Tree p) {
        if (generic(p->op) != INDIR) {
        if (generic(p->op) != INDIR) {
                error("lvalue required\n");
                error("lvalue required\n");
                return value(p);
                return value(p);
        } else if (unqual(p->type) == voidtype)
        } else if (unqual(p->type) == voidtype)
                warning("`%t' used as an lvalue\n", p->type);
                warning("`%t' used as an lvalue\n", p->type);
        return p->kids[0];
        return p->kids[0];
}
}
Tree retype(Tree p, Type ty) {
Tree retype(Tree p, Type ty) {
        Tree q;
        Tree q;
 
 
        if (p->type == ty)
        if (p->type == ty)
                return p;
                return p;
        q = tree(p->op, ty, p->kids[0], p->kids[1]);
        q = tree(p->op, ty, p->kids[0], p->kids[1]);
        q->node = p->node;
        q->node = p->node;
        q->u = p->u;
        q->u = p->u;
        return q;
        return q;
}
}
Tree rightkid(Tree p) {
Tree rightkid(Tree p) {
        while (p && p->op == RIGHT)
        while (p && p->op == RIGHT)
                if (p->kids[1])
                if (p->kids[1])
                        p = p->kids[1];
                        p = p->kids[1];
                else if (p->kids[0])
                else if (p->kids[0])
                        p = p->kids[0];
                        p = p->kids[0];
                else
                else
                        assert(0);
                        assert(0);
        assert(p);
        assert(p);
        return p;
        return p;
}
}
int hascall(Tree p) {
int hascall(Tree p) {
        if (p == 0)
        if (p == 0)
                return 0;
                return 0;
        if (generic(p->op) == CALL || (IR->mulops_calls &&
        if (generic(p->op) == CALL || (IR->mulops_calls &&
          (p->op == DIV+I || p->op == MOD+I || p->op == MUL+I
          (p->op == DIV+I || p->op == MOD+I || p->op == MUL+I
        || p->op == DIV+U || p->op == MOD+U || p->op == MUL+U)))
        || p->op == DIV+U || p->op == MOD+U || p->op == MUL+U)))
                return 1;
                return 1;
        return hascall(p->kids[0]) || hascall(p->kids[1]);
        return hascall(p->kids[0]) || hascall(p->kids[1]);
}
}
Type binary(Type xty, Type yty) {
Type binary(Type xty, Type yty) {
#define xx(t) if (xty == t || yty == t) return t
#define xx(t) if (xty == t || yty == t) return t
        xx(longdouble);
        xx(longdouble);
        xx(doubletype);
        xx(doubletype);
        xx(floattype);
        xx(floattype);
        xx(unsignedlonglong);
        xx(unsignedlonglong);
        xx(longlong);
        xx(longlong);
        xx(unsignedlong);
        xx(unsignedlong);
        if (xty == longtype     && yty == unsignedtype
        if (xty == longtype     && yty == unsignedtype
        ||  xty == unsignedtype && yty == longtype)
        ||  xty == unsignedtype && yty == longtype)
                if (longtype->size > unsignedtype->size)
                if (longtype->size > unsignedtype->size)
                        return longtype;
                        return longtype;
                else
                else
                        return unsignedlong;
                        return unsignedlong;
        xx(longtype);
        xx(longtype);
        xx(unsignedtype);
        xx(unsignedtype);
        return inttype;
        return inttype;
#undef xx
#undef xx
}
}
Tree pointer(Tree p) {
Tree pointer(Tree p) {
        if (isarray(p->type))
        if (isarray(p->type))
                /* assert(p->op != RIGHT || p->u.sym == NULL), */
                /* assert(p->op != RIGHT || p->u.sym == NULL), */
                p = retype(p, atop(p->type));
                p = retype(p, atop(p->type));
        else if (isfunc(p->type))
        else if (isfunc(p->type))
                p = retype(p, ptr(p->type));
                p = retype(p, ptr(p->type));
        return p;
        return p;
}
}
Tree cond(Tree p) {
Tree cond(Tree p) {
        int op = generic(rightkid(p)->op);
        int op = generic(rightkid(p)->op);
 
 
        if (op == AND || op == OR || op == NOT
        if (op == AND || op == OR || op == NOT
        ||  op == EQ  || op == NE
        ||  op == EQ  || op == NE
        ||  op == LE  || op == LT || op == GE || op == GT)
        ||  op == LE  || op == LT || op == GE || op == GT)
                return p;
                return p;
        p = pointer(p);
        p = pointer(p);
        return (*optree[NEQ])(NE, p, consttree(0, inttype));
        return (*optree[NEQ])(NE, p, consttree(0, inttype));
}
}
Tree cast(Tree p, Type type) {
Tree cast(Tree p, Type type) {
        Type src, dst;
        Type src, dst;
 
 
        p = value(p);
        p = value(p);
        if (p->type == type)
        if (p->type == type)
                return p;
                return p;
        dst = unqual(type);
        dst = unqual(type);
        src = unqual(p->type);
        src = unqual(p->type);
        if (src->op != dst->op || src->size != dst->size) {
        if (src->op != dst->op || src->size != dst->size) {
                switch (src->op) {
                switch (src->op) {
                case INT:
                case INT:
                        if (src->size < inttype->size)
                        if (src->size < inttype->size)
                                p = simplify(CVI, inttype, p, NULL);
                                p = simplify(CVI, inttype, p, NULL);
                        break;
                        break;
                case UNSIGNED:
                case UNSIGNED:
                        if (src->size < inttype->size)
                        if (src->size < inttype->size)
                                p = simplify(CVU, inttype, p, NULL);
                                p = simplify(CVU, inttype, p, NULL);
                        else if (src->size < unsignedtype->size)
                        else if (src->size < unsignedtype->size)
                                p = simplify(CVU, unsignedtype, p, NULL);
                                p = simplify(CVU, unsignedtype, p, NULL);
                        break;
                        break;
                case ENUM:
                case ENUM:
                        p = retype(p, inttype);
                        p = retype(p, inttype);
                        break;
                        break;
                case POINTER:
                case POINTER:
                        if (isint(dst) && src->size > dst->size)
                        if (isint(dst) && src->size > dst->size)
                                warning("conversion from `%t' to `%t' is undefined\n", p->type, type);
                                warning("conversion from `%t' to `%t' is undefined\n", p->type, type);
                        p = simplify(CVP, super(src), p, NULL);
                        p = simplify(CVP, super(src), p, NULL);
                        break;
                        break;
                case FLOAT:
                case FLOAT:
                        break;
                        break;
                default: assert(0);
                default: assert(0);
                }
                }
                {
                {
                        src = unqual(p->type);
                        src = unqual(p->type);
                        dst = super(dst);
                        dst = super(dst);
                        if (src->op != dst->op)
                        if (src->op != dst->op)
                                switch (src->op) {
                                switch (src->op) {
                                case INT:
                                case INT:
                                        p = simplify(CVI, dst, p, NULL);
                                        p = simplify(CVI, dst, p, NULL);
                                        break;
                                        break;
                                case UNSIGNED:
                                case UNSIGNED:
                                        if (isfloat(dst)) {
                                        if (isfloat(dst)) {
                                                Type ssrc = signedint(src);
                                                Type ssrc = signedint(src);
                                                Tree two = cnsttree(longdouble, (long double)2.0);
                                                Tree two = cnsttree(longdouble, (long double)2.0);
                                                p = (*optree['+'])(ADD,
                                                p = (*optree['+'])(ADD,
                                                        (*optree['*'])(MUL,
                                                        (*optree['*'])(MUL,
                                                                two,
                                                                two,
                                                                simplify(CVU, ssrc,
                                                                simplify(CVU, ssrc,
                                                                        simplify(RSH, src,
                                                                        simplify(RSH, src,
                                                                                p, consttree(1, inttype)), NULL)),
                                                                                p, consttree(1, inttype)), NULL)),
                                                        simplify(CVU, ssrc,
                                                        simplify(CVU, ssrc,
                                                                simplify(BAND, src,
                                                                simplify(BAND, src,
                                                                        p, consttree(1, unsignedtype)), NULL));
                                                                        p, consttree(1, unsignedtype)), NULL));
                                        } else
                                        } else
                                                p = simplify(CVU, dst, p, NULL);
                                                p = simplify(CVU, dst, p, NULL);
                                        break;
                                        break;
                                case FLOAT:
                                case FLOAT:
                                        if (isunsigned(dst)) {
                                        if (isunsigned(dst)) {
                                                Type sdst = signedint(dst);
                                                Type sdst = signedint(dst);
                                                Tree c = cast(cnsttree(longdouble, (long double)sdst->u.sym->u.limits.max.i + 1), src);
                                                Tree c = cast(cnsttree(longdouble, (long double)sdst->u.sym->u.limits.max.i + 1), src);
                                                p = condtree(
                                                p = condtree(
                                                        simplify(GE, src, p, c),
                                                        simplify(GE, src, p, c),
                                                        (*optree['+'])(ADD,
                                                        (*optree['+'])(ADD,
                                                                cast(cast(simplify(SUB, src, p, c), sdst), dst),
                                                                cast(cast(simplify(SUB, src, p, c), sdst), dst),
                                                                cast(cnsttree(unsignedlong, (unsigned long)sdst->u.sym->u.limits.max.i + 1), dst)),
                                                                cast(cnsttree(unsignedlong, (unsigned long)sdst->u.sym->u.limits.max.i + 1), dst)),
                                                        simplify(CVF, sdst, p, NULL));
                                                        simplify(CVF, sdst, p, NULL));
                                        } else
                                        } else
                                                p = simplify(CVF, dst, p, NULL);
                                                p = simplify(CVF, dst, p, NULL);
                                        break;
                                        break;
                                default: assert(0);
                                default: assert(0);
                                }
                                }
                        dst = unqual(type);
                        dst = unqual(type);
                }
                }
        }
        }
        src = unqual(p->type);
        src = unqual(p->type);
        switch (src->op) {
        switch (src->op) {
        case INT:
        case INT:
                if (src->op != dst->op || src->size != dst->size)
                if (src->op != dst->op || src->size != dst->size)
                        p = simplify(CVI, dst, p, NULL);
                        p = simplify(CVI, dst, p, NULL);
                break;
                break;
        case UNSIGNED:
        case UNSIGNED:
                if (src->op != dst->op || src->size != dst->size)
                if (src->op != dst->op || src->size != dst->size)
                        p = simplify(CVU, dst, p, NULL);
                        p = simplify(CVU, dst, p, NULL);
                break;
                break;
        case FLOAT:
        case FLOAT:
                if (src->op != dst->op || src->size != dst->size)
                if (src->op != dst->op || src->size != dst->size)
                        p = simplify(CVF, dst, p, NULL);
                        p = simplify(CVF, dst, p, NULL);
                break;
                break;
        case POINTER:
        case POINTER:
                if (src->op != dst->op)
                if (src->op != dst->op)
                        p = simplify(CVP, dst, p, NULL);
                        p = simplify(CVP, dst, p, NULL);
                else {
                else {
                        if (isfunc(src->type) && !isfunc(dst->type)
                        if (isfunc(src->type) && !isfunc(dst->type)
                        || !isfunc(src->type) &&  isfunc(dst->type))
                        || !isfunc(src->type) &&  isfunc(dst->type))
                                warning("conversion from `%t' to `%t' is compiler dependent\n", p->type, type);
                                warning("conversion from `%t' to `%t' is compiler dependent\n", p->type, type);
 
 
                        if (src->size != dst->size)
                        if (src->size != dst->size)
                                p = simplify(CVP, dst, p, NULL);
                                p = simplify(CVP, dst, p, NULL);
                }
                }
                break;
                break;
        default: assert(0);
        default: assert(0);
        }
        }
        return retype(p, type);
        return retype(p, type);
}
}
Tree field(Tree p, const char *name) {
Tree field(Tree p, const char *name) {
        Field q;
        Field q;
        Type ty1, ty = p->type;
        Type ty1, ty = p->type;
 
 
        if (isptr(ty))
        if (isptr(ty))
                ty = deref(ty);
                ty = deref(ty);
        ty1 = ty;
        ty1 = ty;
        ty = unqual(ty);
        ty = unqual(ty);
        if ((q = fieldref(name, ty)) != NULL) {
        if ((q = fieldref(name, ty)) != NULL) {
                if (isarray(q->type)) {
                if (isarray(q->type)) {
                        ty = q->type->type;
                        ty = q->type->type;
                        if (isconst(ty1) && !isconst(ty))
                        if (isconst(ty1) && !isconst(ty))
                                ty = qual(CONST, ty);
                                ty = qual(CONST, ty);
                        if (isvolatile(ty1) && !isvolatile(ty))
                        if (isvolatile(ty1) && !isvolatile(ty))
                                ty = qual(VOLATILE, ty);
                                ty = qual(VOLATILE, ty);
                        ty = array(ty, q->type->size/ty->size, q->type->align);
                        ty = array(ty, q->type->size/ty->size, q->type->align);
                } else {
                } else {
                        ty = q->type;
                        ty = q->type;
                        if (isconst(ty1) && !isconst(ty))
                        if (isconst(ty1) && !isconst(ty))
                                ty = qual(CONST, ty);
                                ty = qual(CONST, ty);
                        if (isvolatile(ty1) && !isvolatile(ty))
                        if (isvolatile(ty1) && !isvolatile(ty))
                                ty = qual(VOLATILE, ty);
                                ty = qual(VOLATILE, ty);
                        ty = ptr(ty);
                        ty = ptr(ty);
                }
                }
                if (YYcheck && !isaddrop(p->op) && q->offset > 0)        /* omit */
                if (YYcheck && !isaddrop(p->op) && q->offset > 0)        /* omit */
                        p = nullcall(ty, YYcheck, p, consttree(q->offset, inttype));    /* omit */
                        p = nullcall(ty, YYcheck, p, consttree(q->offset, inttype));    /* omit */
                else                                    /* omit */
                else                                    /* omit */
                p = simplify(ADD+P, ty, p, consttree(q->offset, signedptr));
                p = simplify(ADD+P, ty, p, consttree(q->offset, signedptr));
 
 
                if (q->lsb) {
                if (q->lsb) {
                        p = tree(FIELD, ty->type, rvalue(p), NULL);
                        p = tree(FIELD, ty->type, rvalue(p), NULL);
                        p->u.field = q;
                        p->u.field = q;
                } else if (!isarray(q->type))
                } else if (!isarray(q->type))
                        p = rvalue(p);
                        p = rvalue(p);
 
 
        } else {
        } else {
                error("unknown field `%s' of `%t'\n", name, ty);
                error("unknown field `%s' of `%t'\n", name, ty);
                p = rvalue(retype(p, ptr(inttype)));
                p = rvalue(retype(p, ptr(inttype)));
        }
        }
        return p;
        return p;
}
}
/* funcname - return name of function f or a function' */
/* funcname - return name of function f or a function' */
char *funcname(Tree f) {
char *funcname(Tree f) {
        if (isaddrop(f->op))
        if (isaddrop(f->op))
                return stringf("`%s'", f->u.sym->name);
                return stringf("`%s'", f->u.sym->name);
        return "a function";
        return "a function";
}
}
static Tree nullcheck(Tree p) {
static Tree nullcheck(Tree p) {
        if (!needconst && YYnull && isptr(p->type)) {
        if (!needconst && YYnull && isptr(p->type)) {
                p = value(p);
                p = value(p);
                if (strcmp(YYnull->name, "_YYnull") == 0) {
                if (strcmp(YYnull->name, "_YYnull") == 0) {
                        Symbol t1 = temporary(REGISTER, voidptype);
                        Symbol t1 = temporary(REGISTER, voidptype);
                        p = tree(RIGHT, p->type,
                        p = tree(RIGHT, p->type,
                                tree(OR, voidtype,
                                tree(OR, voidtype,
                                        cond(asgn(t1, cast(p, voidptype))),
                                        cond(asgn(t1, cast(p, voidptype))),
                                        vcall(YYnull, voidtype, (file && *file ? pointer(idtree(mkstr(file)->u.c.loc)) : cnsttree(voidptype, NULL)), cnsttree(inttype, (long)lineno)            , NULL)),
                                        vcall(YYnull, voidtype, (file && *file ? pointer(idtree(mkstr(file)->u.c.loc)) : cnsttree(voidptype, NULL)), cnsttree(inttype, (long)lineno)            , NULL)),
                                idtree(t1));
                                idtree(t1));
                }
                }
 
 
                else
                else
                        p = nullcall(p->type, YYnull, p, cnsttree(inttype, 0L));
                        p = nullcall(p->type, YYnull, p, cnsttree(inttype, 0L));
 
 
        }
        }
        return p;
        return p;
}
}
Tree nullcall(Type pty, Symbol f, Tree p, Tree e) {
Tree nullcall(Type pty, Symbol f, Tree p, Tree e) {
        Type ty;
        Type ty;
 
 
        if (isarray(pty))
        if (isarray(pty))
                return retype(nullcall(atop(pty), f, p, e), pty);
                return retype(nullcall(atop(pty), f, p, e), pty);
        ty = unqual(unqual(p->type)->type);
        ty = unqual(unqual(p->type)->type);
        return vcall(f, pty,
        return vcall(f, pty,
                p, e,
                p, e,
                cnsttree(inttype, (long)ty->size),
                cnsttree(inttype, (long)ty->size),
                cnsttree(inttype, (long)ty->align),
                cnsttree(inttype, (long)ty->align),
                (file && *file ? pointer(idtree(mkstr(file)->u.c.loc)) : cnsttree(voidptype, NULL)), cnsttree(inttype, (long)lineno)            , NULL);
                (file && *file ? pointer(idtree(mkstr(file)->u.c.loc)) : cnsttree(voidptype, NULL)), cnsttree(inttype, (long)lineno)            , NULL);
}
}
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.