⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 expr.c

📁 把pascal程序转成C语言程序 把pascal程序转成C语言程序
💻 C
📖 第 1 页 / 共 5 页
字号:
                    return a;                }            } else {                if (dolongcast(a->args[i], tolong))                    return a;            }            break;        case EK_AND:  /* operators which always return int */        case EK_OR:        case EK_EQ:        case EK_NE:        case EK_LT:        case EK_GT:        case EK_LE:        case EK_GE:            if (tolong&1)                break;            return a;	default:	    break;    }    return NULL;}/* Return -1 if short int or plain int, 1 if long, 0 if can't tell */int exprlongness(ex)Expr *ex;{    if (sizeof_int >= 32)        return -1;    return (dolongcast(ex, 3) != NULL) -           (dolongcast(ex, 2) != NULL);}Expr *makeexpr_longcast(a, tolong)Expr *a;int tolong;{    Expr *ex;    Type *type;    if (sizeof_int >= 32)        return a;    type = ord_type(a->val.type);    if (type->kind != TK_INTEGER && type->kind != TK_SMALLSET)        return a;    a = makeexpr_unlongcast(a);    if (tolong) {        ex = dolongcast(a, 1);    } else {        ex = dolongcast(copyexpr(a), 0);        if (ex) {            if (!dolongcast(ex, 2)) {                freeexpr(ex);                ex = NULL;            }        }    }    if (ex)        return ex;    return makeexpr_un(EK_CAST, (tolong) ? tp_integer : tp_int, a);}Expr *makeexpr_arglong(a, tolong)Expr *a;int tolong;{    int cast = castlongargs;    if (cast < 0)	cast = castargs;    if (cast > 0 || (cast < 0 && prototypes == 0)) {	return makeexpr_longcast(a, tolong);    }    return a;}Expr *makeexpr_unlongcast(a)Expr *a;{    switch (a->kind) {        case EK_LONGCONST:            if (a->val.i >= -32767 && a->val.i <= 32767)                a->kind = EK_CONST;            break;        case EK_CAST:            if ((a->val.type == tp_integer ||                 a->val.type == tp_int) &&                ord_type(a->args[0]->val.type)->kind == TK_INTEGER) {                a = grabarg(a, 0);            }            break;        default:	    break;    }    return a;}Expr *makeexpr_forcelongness(a)    /* force a to have a definite longness */Expr *a;{    Expr *ex;    ex = makeexpr_unlongcast(copyexpr(a));    if (exprlongness(ex)) {        freeexpr(a);        return ex;    }    freeexpr(ex);    if (exprlongness(a) == 0)        return makeexpr_longcast(a, 1);    else        return a;}Expr *makeexpr_ord(ex)Expr *ex;{    ex = makeexpr_charcast(ex);    switch (ord_type(ex->val.type)->kind) {        case TK_ENUM:            return makeexpr_cast(ex, tp_int);        case TK_CHAR:            if (ex->kind == EK_CONST &&                (ex->val.i >= 32 && ex->val.i < 127)) {                insertarg(&ex, 0, makeexpr_name("'%lc'", tp_integer));            }            ex->val.type = tp_int;            return ex;        case TK_BOOLEAN:            ex->val.type = tp_int;            return ex;        case TK_POINTER:            return makeexpr_cast(ex, tp_integer);        default:            return ex;    }}/* Tell whether an expression "looks" negative */int expr_looks_neg(ex)Expr *ex;{    int i;    switch (ex->kind) {        case EK_NEG:            return 1;        case EK_CONST:        case EK_LONGCONST:            switch (ord_type(ex->val.type)->kind) {                case TK_INTEGER:                case TK_CHAR:                    return (ex->val.i < 0);                case TK_REAL:                    return (ex->val.s && ex->val.s[0] == '-');                default:                    return 0;            }        case EK_TIMES:        case EK_DIVIDE:            for (i = 0; i < ex->nargs; i++) {                if (expr_looks_neg(ex->args[i]))                    return 1;            }            return 0;        case EK_CAST:            return expr_looks_neg(ex->args[0]);        default:            return 0;    }}/* Tell whether an expression is probably negative */int expr_is_neg(ex)Expr *ex;{    int i;    i = possiblesigns(ex) & (1|4);    if (i == 1)	return 1;    /* if expression really is negative! */    if (i == 4)	return 0;    /* if expression is definitely positive. */    return expr_looks_neg(ex);}int expr_neg_cost(a)Expr *a;{    int i, c;    switch (a->kind) {        case EK_CONST:        case EK_LONGCONST:            switch (ord_type(a->val.type)->kind) {                case TK_INTEGER:                case TK_CHAR:                case TK_REAL:                    return 0;		default:		    return 1;            }        case EK_NEG:            return -1;        case EK_TIMES:        case EK_DIVIDE:            for (i = 0; i < a->nargs; i++) {                c = expr_neg_cost(a->args[i]);                if (c <= 0)                    return c;            }            return 1;        case EK_PLUS:            for (i = 0; i < a->nargs; i++) {                if (expr_looks_neg(a->args[i]))                    return 0;            }            return 1;        default:            return 1;    }}Expr *enum_to_int(a)Expr *a;{    if (ord_type(a->val.type)->kind == TK_ENUM) {        if (a->kind == EK_CAST &&             ord_type(a->args[0]->val.type)->kind == TK_INTEGER)            return grabarg(a, 0);        else            return makeexpr_cast(a, tp_integer);    } else        return a;}Expr *neg_inside_sum(a)Expr *a;{    int i;    for (i = 0; i < a->nargs; i++)        a->args[i] = makeexpr_neg(a->args[i]);    return a;}Expr *makeexpr_neg(a)Expr *a;{    int i;    if (debug>2) { fprintf(outf,"makeexpr_neg("); dumpexpr(a); fprintf(outf,")\n"); }    a = enum_to_int(a);    switch (a->kind) {        case EK_CONST:        case EK_LONGCONST:            switch (ord_type(a->val.type)->kind) {                case TK_INTEGER:                case TK_CHAR:                    if (a->val.i == MININT)                        valrange();                    else                        a->val.i = - a->val.i;                    return a;                case TK_REAL:                    if (!realzero(a->val.s)) {                        if (a->val.s[0] == '-')                            strchange(&a->val.s, a->val.s+1);                        else                            strchange(&a->val.s, format_s("-%s", a->val.s));                    }                    return a;		default:		    break;            }            break;        case EK_PLUS:            if (expr_neg_cost(a) <= 0)                return neg_inside_sum(a);            break;        case EK_TIMES:        case EK_DIVIDE:            for (i = 0; i < a->nargs; i++) {                if (expr_neg_cost(a->args[i]) <= 0) {                    a->args[i] = makeexpr_neg(a->args[i]);                    return a;                }            }            break;        case EK_CAST:            if (a->val.type != tp_unsigned &&                 a->val.type != tp_uint &&                 a->val.type != tp_ushort &&                 a->val.type != tp_ubyte &&                 a->args[0]->val.type != tp_unsigned &&                 a->args[0]->val.type != tp_uint &&                 a->args[0]->val.type != tp_ushort &&                 a->args[0]->val.type != tp_ubyte &&                 expr_looks_neg(a->args[0])) {                a->args[0] = makeexpr_neg(a->args[0]);                return a;            }            break;        case EK_NEG:            return grabarg(a, 0);	default:	    break;    }    return makeexpr_un(EK_NEG, promote_type(a->val.type), a);}#define ISCONST(kind) ((kind)==EK_CONST || (kind)==EK_LONGCONST)#define MOVCONST(ex) (ISCONST((ex)->kind) && (ex)->val.type->kind != TK_STRING)#define COMMUTATIVE (kind != EK_COMMA && type->kind != TK_REAL)Type *true_type(ex)Expr *ex;{    Meaning *mp;    Type *type, *tp;    while (ex->kind == EK_CAST)	ex = ex->args[0];    type = ex->val.type;    if (ex->kind == EK_VAR || ex->kind == EK_FUNCTION || ex->kind == EK_DOT) {	mp = (Meaning *)ex->val.i;	if (mp && mp->type && mp->type->kind != TK_VOID)	    type = mp->type;    }    if (ex->kind == EK_INDEX) {	tp = true_type(ex->args[0]);	if ((tp->kind == TK_ARRAY || tp->kind == TK_SMALLARRAY ||	     tp->kind == TK_STRING) &&	    tp->basetype && tp->basetype->kind != TK_VOID)	    type = tp->basetype;    }    if (type->kind == TK_SUBR)	type = findbasetype(type, ODECL_NOPRES);    return type;}int ischartype(ex)Expr *ex;{    if (ord_type(ex->val.type)->kind == TK_CHAR)	return 1;    if (true_type(ex)->kind == TK_CHAR)	return 1;    if (ISCONST(ex->kind) && ex->nargs > 0 &&	ex->args[0]->kind == EK_NAME &&	ex->args[0]->val.s[0] == '\'')	return 1;    return 0;}Static Expr *commute(a, b, kind)Expr *a, *b;enum exprkind kind;{    int i, di;    Type *type;    if (debug>2) { fprintf(outf,"commute("); dumpexpr(a); fprintf(outf,", "); dumpexpr(b); fprintf(outf,")\n"); }#if 1    type = promote_type_bin(a->val.type, b->val.type);#else    type = a->val.type;    if (b->val.type->kind == TK_REAL)        type = b->val.type;#endif    if (MOVCONST(a) && !MOVCONST(b) && COMMUTATIVE)        swapexprs(a, b);                /* put constant last */    if (a->kind == kind) {        di = (MOVCONST(a->args[a->nargs-1]) && COMMUTATIVE) ? -1 : 0;        if (b->kind == kind) {            for (i = 0; i < b->nargs; i++)                insertarg(&a, a->nargs + di, b->args[i]);            FREE(b);        } else            insertarg(&a, a->nargs + di, b);        a->val.type = type;    } else if (b->kind == kind) {        if (MOVCONST(a) && COMMUTATIVE)            insertarg(&b, b->nargs, a);        else            insertarg(&b, 0, a);        a = b;        a->val.type = type;    } else {        a = makeexpr_bin(kind, type, a, b);    }    if (debug>2) { fprintf(outf,"commute returns "); dumpexpr(a); fprintf(outf,"\n"); }    return a;}int chararith = 0;Expr *makeexpr_plus(a, b)Expr *a, *b;{    int i, j, k, castdouble = 0;    Type *type;    if (debug>2) { fprintf(outf,"makeexpr_plus("); dumpexpr(a); fprintf(outf,", "); dumpexpr(b); fprintf(outf,")\n"); }    if (!a)        return b;    if (!b)        return a;    if (a->kind == EK_NEG && a->args[0]->kind == EK_PLUS)        a = neg_inside_sum(grabarg(a, 0));    if (b->kind == EK_NEG && b->args[0]->kind == EK_PLUS)        b = neg_inside_sum(grabarg(b, 0));    a = commute(enum_to_int(a), enum_to_int(b), EK_PLUS);    type = NULL;    for (i = 0; i < a->nargs; i++) {        if (ord_type(a->args[i]->val.type)->kind == TK_CHAR ||            a->args[i]->val.type->kind == TK_POINTER ||            a->args[i]->val.type->kind == TK_STRING) {   /* for string literals */            if (type == ord_type(a->args[i]->val.type))                type = tp_integer;   /* 'z'-'a' and p1-p2 are integers */            else                type = ord_type(a->args[i]->val.type);        }    }    if (type)        a->val.type = type;    for (i = 0; i < a->nargs && !ISCONST(a->args[i]->kind); i++) ;    if (i < a->nargs-1) {        for (j = i+1; j < a->nargs; j++) {            if (ISCONST(a->args[j]->kind)) {                if ((ord_type(a->args[i]->val.type) == ord_type(a->args[j]->val.type) ||		     ord_type(a->args[i]->val.type)->kind == TK_INTEGER ||		     ord_type(a->args[j]->val.type)->kind == TK_INTEGER) &&		    (!(ischartype(a->args[i]) || ischartype(a->args[j])) ||		     chararith ||		     a->args[i]->val.i == - a->args[j]->val.i ||		     a->args[i]->val.i == 0 || a->args[j]->val.i == 0) &&                    (a->args[i]->val.type->kind != TK_REAL &&                     a->args[i]->val.type->kind != TK_STRING &&                     a->args[j]->val.type->kind != TK_REAL &&                     a->args[j]->val.type->kind != TK_STRING)) {                    a->args[i]->val.i += a->args[j]->val.i;                    delfreearg(&a, j);                    j--;                } else if (a->args[i]->val.type->kind == TK_STRING &&                           ord_type(a->args[j]->val.type)->kind == TK_INTEGER &&                           a->args[j]->val.i < 0 &&                           a->args[j]->val.i >= -stringleaders) {                    /* strictly speaking, the following is illegal pointer arithmetic */                    a->args[i] = makeexpr_lstring(a->args[i]->val.s + a->args[j]->val.i,                                                  a->args[i]->val.i - a->args[j]->val.i);                    for (k = 0; k < - a->args[j]->val.i; k++)                        a->args[i]->val.s[k] = '>';                    delfreearg(&a, j);                    j--;                }            }        }    }    if (checkconst(a->args[a->nargs-1], 0)) {	if (a->args[a->nargs-1]->val.type->kind == TK_REAL &&	    a->args[0]->val.type->kind != TK_REAL)	    castdouble = 1;        delfreearg(&a, a->nargs-1);    }    for (i = 0; i < a->nargs; i++) {        if (a->args[i]->kind == EK_NEG && nosideeffects(a->args[i], 1)) {            for (j = 0; j < a->nargs; j++) {                if (exprsame(a->args[j], a->args[i]->args[0], 1)) {                    delfreearg(&a, i);                    if (i < j) j--; else i--;                    delfreearg(&a, j);                    i--;                    break;                }            }        }    }    if (a->nargs == 0) {	type = a->val.type;	FREE(a);	a = gentle_cast(makeexpr_long(0), type);	a->val.type = type;	return a;    } else if (a->nargs == 1) {	b = a->args[0];	FREE(a);	a = b;    } else {	if (a->nargs == 2 && ISCONST(a->args[1]->kind) &&	    a->args[1]->val.i <= -127 &&	    true_type(a->args[0]) == tp_char && signedchars != 0) {	    a->args[0] = force_unsigned(a->args[0]);	}	if (a->nargs > 2 &&	    ISCONST(a->args[a->nargs-1]->kind) &&	    ISCONST(a->args[a->nargs-2]->kind) &&	    ischartype(a->args[a->nargs-1]) &&	    ischartype(a->args[a->nargs-2])) {	    i = a->args[a->nargs-1]->val.i;	    j = a->args[a->nargs-2]->val.i;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -