|
|
1.1 root 1: # include "mfile1"
2:
3: # define SWAP(p,q) {sp=p; p=q; q=sp;}
4: # define RCON(p) (p->in.right->in.op==ICON)
5: # define RO(p) p->in.right->in.op
6: # define RV(p) p->in.right->tn.lval
7: # define LCON(p) (p->in.left->in.op==ICON)
8: # define LO(p) p->in.left->in.op
9: # define LV(p) p->in.left->tn.lval
10:
11: int oflag = 0;
12:
13: NODE *
14: fortarg( p ) NODE *p; {
15: /* fortran function arguments */
16:
17: if( p->in.op == CM ){
18: p->in.left = fortarg( p->in.left );
19: p->in.right = fortarg( p->in.right );
20: return(p);
21: }
22:
23: while( ISPTR(p->in.type) ){
24: p = buildtree( UNARY MUL, p, NIL );
25: }
26: return( optim(p) );
27: }
28:
29: /* mapping relationals when the sides are reversed */
30: short revrel[] ={ EQ, NE, GE, GT, LE, LT, UGE, UGT, ULE, ULT };
31: NODE *
32: optim(p) register NODE *p; {
33: /* local optimizations, most of which are probably machine independent */
34:
35: register o, ty;
36: NODE *sp;
37: int i;
38: TWORD t;
39:
40: if( (t=BTYPE(p->in.type))==ENUMTY || t==MOETY ) econvert(p);
41: if( oflag ) return(p);
42: ty = optype( o=p->in.op);
43: if( ty == LTYPE ) return(p);
44:
45: if( ty == BITYPE ) p->in.right = optim(p->in.right);
46: p->in.left = optim(p->in.left);
47:
48: /* collect constants */
49:
50: switch(o){
51:
52: case SCONV:
53: case PCONV:
54: return( clocal(p) );
55:
56: case FORTCALL:
57: p->in.right = fortarg( p->in.right );
58: break;
59:
60: case UNARY AND:
61: if( LO(p) != NAME ) cerror( "& error" );
62:
63: if( !andable(p->in.left) ) return(p);
64:
65: LO(p) = ICON;
66:
67: setuleft:
68: /* paint over the type of the left hand side with the type of the top */
69: p->in.left->in.type = p->in.type;
70: p->in.left->fn.cdim = p->fn.cdim;
71: p->in.left->fn.csiz = p->fn.csiz;
72: p->in.op = FREE;
73: return( p->in.left );
74:
75: case UNARY MUL:
76: if( LO(p) != ICON ) break;
77: LO(p) = NAME;
78: goto setuleft;
79:
80: case MINUS:
81: if( !nncon(p->in.right) ) break;
82: RV(p) = -RV(p);
83: o = p->in.op = PLUS;
84:
85: case MUL:
86: case PLUS:
87: case AND:
88: case OR:
89: case ER:
90: /* commutative ops; for now, just collect constants */
91: /* someday, do it right */
92: if( nncon(p->in.left) || ( LCON(p) && !RCON(p) ) ) SWAP( p->in.left, p->in.right );
93: /* make ops tower to the left, not the right */
94: if( RO(p) == o ){
95: NODE *t1, *t2, *t3;
96: t1 = p->in.left;
97: sp = p->in.right;
98: t2 = sp->in.left;
99: t3 = sp->in.right;
100: /* now, put together again */
101: p->in.left = sp;
102: sp->in.left = t1;
103: sp->in.right = t2;
104: p->in.right = t3;
105: }
106: if(o == PLUS && LO(p) == MINUS && RCON(p) && RCON(p->in.left) &&
107: conval(p->in.right, MINUS, p->in.left->in.right)){
108: zapleft:
109: RO(p->in.left) = FREE;
110: LO(p) = FREE;
111: p->in.left = p->in.left->in.left;
112: }
113: if( RCON(p) && LO(p)==o && RCON(p->in.left) && conval( p->in.right, o, p->in.left->in.right ) ){
114: goto zapleft;
115: }
116: else if( LCON(p) && RCON(p) && conval( p->in.left, o, p->in.right ) ){
117: zapright:
118: RO(p) = FREE;
119: p->in.left = makety( p->in.left, p->in.type, p->fn.cdim, p->fn.csiz );
120: p->in.op = FREE;
121: return( clocal( p->in.left ) );
122: }
123:
124: /* change muls to shifts */
125:
126: if( o==MUL && nncon(p->in.right) && (i=ispow2(RV(p)))>=0){
127: if( i == 0 ){ /* multiplication by 1 */
128: goto zapright;
129: }
130: o = p->in.op = LS;
131: p->in.right->in.type = p->in.right->fn.csiz = INT;
132: RV(p) = i;
133: }
134:
135: /* change +'s of negative consts back to - */
136: if( o==PLUS && nncon(p->in.right) && RV(p)<0 ){
137: RV(p) = -RV(p);
138: o = p->in.op = MINUS;
139: }
140: break;
141:
142: case DIV:
143: if( nncon( p->in.right ) && p->in.right->tn.lval == 1 ) goto zapright;
144: break;
145:
146: case EQ:
147: case NE:
148: case LT:
149: case LE:
150: case GT:
151: case GE:
152: case ULT:
153: case ULE:
154: case UGT:
155: case UGE:
156: if( !LCON(p) ) break;
157:
158: /* exchange operands */
159:
160: sp = p->in.left;
161: p->in.left = p->in.right;
162: p->in.right = sp;
163: p->in.op = revrel[p->in.op - EQ ];
164: break;
165:
166: }
167:
168: return(p);
169: }
170:
171: ispow2( c ) CONSZ c; {
172: register i;
173: if( c <= 0 || (c&(c-1)) ) return(-1);
174: for( i=0; c>1; ++i) c >>= 1;
175: return(i);
176: }
177:
178: nncon( p ) NODE *p; {
179: /* is p a constant without a name */
180: return( p->in.op == ICON && p->tn.rval == NONAME );
181: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.