LEFT | RIGHT |
(no file at all) | |
1 // Inferno utils/5c/peep.c | 1 // Inferno utils/5c/peep.c |
2 // http://code.google.com/p/inferno-os/source/browse/utils/5g/peep.c | 2 // http://code.google.com/p/inferno-os/source/browse/utils/5g/peep.c |
3 // | 3 // |
4 // Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved. | 4 // Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved. |
5 // Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net) | 5 // Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net) |
6 // Portions Copyright © 1997-1999 Vita Nuova Limited | 6 // Portions Copyright © 1997-1999 Vita Nuova Limited |
7 // Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuov
a.com) | 7 // Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuov
a.com) |
8 // Portions Copyright © 2004,2006 Bruce Ellis | 8 // Portions Copyright © 2004,2006 Bruce Ellis |
9 // Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net) | 9 // Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net) |
10 // Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others | 10 // Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others |
(...skipping 30 matching lines...) Expand all Loading... |
41 | 41 |
42 void | 42 void |
43 peep(void) | 43 peep(void) |
44 { | 44 { |
45 Reg *r, *r1, *r2; | 45 Reg *r, *r1, *r2; |
46 Prog *p, *p1; | 46 Prog *p, *p1; |
47 int t; | 47 int t; |
48 /* | 48 /* |
49 * complete R structure | 49 * complete R structure |
50 */ | 50 */ |
51 t = 0; | |
52 for(r=firstr; r!=R; r=r1) { | 51 for(r=firstr; r!=R; r=r1) { |
53 r1 = r->link; | 52 r1 = r->link; |
54 if(r1 == R) | 53 if(r1 == R) |
55 break; | 54 break; |
56 p = r->prog->link; | 55 p = r->prog->link; |
57 while(p != r1->prog) | 56 while(p != r1->prog) |
58 switch(p->as) { | 57 switch(p->as) { |
59 default: | 58 default: |
60 r2 = rega(); | 59 r2 = rega(); |
61 r->link = r2; | 60 r->link = r2; |
62 r2->link = r1; | 61 r2->link = r1; |
63 | 62 |
64 r2->prog = p; | 63 r2->prog = p; |
65 r2->p1 = r; | 64 r2->p1 = r; |
66 r->s1 = r2; | 65 r->s1 = r2; |
67 r2->s1 = r1; | 66 r2->s1 = r1; |
68 r1->p1 = r2; | 67 r1->p1 = r2; |
69 | 68 |
70 r = r2; | 69 r = r2; |
71 t++; | |
72 | 70 |
73 case ADATA: | 71 case ADATA: |
74 case AGLOBL: | 72 case AGLOBL: |
75 case ANAME: | 73 case ANAME: |
76 case ASIGNAME: | 74 case ASIGNAME: |
77 p = p->link; | 75 p = p->link; |
78 } | 76 } |
79 } | 77 } |
| 78 //dumpit("begin", firstr); |
80 | 79 |
81 loop1: | 80 loop1: |
| 81 |
82 t = 0; | 82 t = 0; |
83 for(r=firstr; r!=R; r=r->link) { | 83 for(r=firstr; r!=R; r=r->link) { |
84 p = r->prog; | 84 p = r->prog; |
85 switch(p->as) { | 85 switch(p->as) { |
86 case ASLL: | 86 case ASLL: |
87 case ASRL: | 87 case ASRL: |
88 case ASRA: | 88 case ASRA: |
89 /* | 89 /* |
90 * elide shift into D_SHIFT operand of subsequent instru
ction | 90 * elide shift into D_SHIFT operand of subsequent instru
ction |
91 */ | 91 */ |
92 // if(shiftprop(r)) { | 92 // if(shiftprop(r)) { |
93 // excise(r); | 93 // excise(r); |
94 // t++; | 94 // t++; |
95 // break; | 95 // break; |
96 // } | 96 // } |
97 break; | 97 break; |
98 | 98 |
99 case AMOVW: | 99 case AMOVW: |
100 case AMOVF: | 100 case AMOVF: |
101 case AMOVD: | 101 case AMOVD: |
102 » » » if(p->scond != C_SCOND_NONE) | 102 » » » if(regtyp(&p->from)) |
103 » » » » break; | 103 » » » if(p->from.type == p->to.type) |
104 » » » if(!regtyp(&p->to)) | 104 » » » if(p->scond == C_SCOND_NONE) { |
105 » » » » break; | 105 » » » » if(copyprop(r)) { |
106 //» » » if(isdconst(&p->from)) { | 106 » » » » » excise(r); |
107 //» » » » constprop(&p->from, &p->to, r->s1); | 107 » » » » » t++; |
108 //» » » » break; | 108 » » » » » break; |
109 //» » » } | 109 » » » » } |
110 » » » if(!regtyp(&p->from)) | 110 » » » » if(subprop(r) && copyprop(r)) { |
111 » » » » break; | 111 » » » » » excise(r); |
112 » » » if(p->from.type != p->to.type) | 112 » » » » » t++; |
113 » » » » break; | 113 » » » » » break; |
114 » » » if(copyprop(r)) { | 114 » » » » } |
115 » » » » excise(r); | 115 » » » } |
116 » » » » t++; | 116 » » » break; |
117 » » » » break; | 117 |
118 » » » } | 118 » » » if(p->scond == C_SCOND_NONE) |
119 » » » if(subprop(r) && copyprop(r)) { | 119 » » » if(regtyp(&p->to)) |
120 » » » » excise(r); | 120 » » » if(isdconst(&p->from)) { |
121 » » » » t++; | 121 » » » » constprop(&p->from, &p->to, r->s1); |
122 » » » » break; | 122 » » » } |
123 » » » } | 123 » » » break; |
124 } | 124 } |
125 } | 125 } |
126 if(t) | 126 if(t) |
127 goto loop1; | 127 goto loop1; |
128 » /* | 128 |
129 » * look for MOVB x,R; MOVB R,R | 129 return; |
130 » */ | 130 |
131 for(r=firstr; r!=R; r=r->link) { | 131 for(r=firstr; r!=R; r=r->link) { |
132 p = r->prog; | 132 p = r->prog; |
133 switch(p->as) { | 133 switch(p->as) { |
134 default: | |
135 continue; | |
136 // case AEOR: | 134 // case AEOR: |
137 // /* | 135 // /* |
138 // * EOR -1,x,y => MVN x,y | 136 // * EOR -1,x,y => MVN x,y |
139 // */ | 137 // */ |
140 // if(isdconst(&p->from) && p->from.offset == -1) { | 138 // if(isdconst(&p->from) && p->from.offset == -1) { |
141 // p->as = AMVN; | 139 // p->as = AMVN; |
142 // p->from.type = D_REG; | 140 // p->from.type = D_REG; |
143 // if(p->reg != NREG) | 141 // if(p->reg != NREG) |
144 // p->from.reg = p->reg; | 142 // p->from.reg = p->reg; |
145 // else | 143 // else |
146 // p->from.reg = p->to.reg; | 144 // p->from.reg = p->to.reg; |
147 // p->reg = NREG; | 145 // p->reg = NREG; |
148 // } | 146 // } |
149 //» » » continue; | 147 //» » » break; |
| 148 |
150 case AMOVH: | 149 case AMOVH: |
151 case AMOVHU: | 150 case AMOVHU: |
152 case AMOVB: | 151 case AMOVB: |
153 case AMOVBU: | 152 case AMOVBU: |
| 153 /* |
| 154 * look for MOVB x,R; MOVB R,R |
| 155 */ |
154 if(p->to.type != D_REG) | 156 if(p->to.type != D_REG) |
155 » » » » continue; | 157 » » » » break; |
| 158 » » » if(r1 == R) |
| 159 » » » » break; |
| 160 » » » p1 = r1->prog; |
| 161 » » » if(p1->as != p->as) |
| 162 » » » » break; |
| 163 » » » if(p1->from.type != D_REG || p1->from.reg != p->to.reg) |
| 164 » » » » break; |
| 165 » » » if(p1->to.type != D_REG || p1->to.reg != p->to.reg) |
| 166 » » » » break; |
| 167 » » » excise(r1); |
156 break; | 168 break; |
157 } | 169 } |
158 r1 = r->link; | 170 r1 = r->link; |
159 if(r1 == R) | |
160 continue; | |
161 p1 = r1->prog; | |
162 if(p1->as != p->as) | |
163 continue; | |
164 if(p1->from.type != D_REG || p1->from.reg != p->to.reg) | |
165 continue; | |
166 if(p1->to.type != D_REG || p1->to.reg != p->to.reg) | |
167 continue; | |
168 excise(r1); | |
169 } | 171 } |
170 | 172 |
171 // for(r=firstr; r!=R; r=r->link) { | 173 // for(r=firstr; r!=R; r=r->link) { |
172 // p = r->prog; | 174 // p = r->prog; |
173 // switch(p->as) { | 175 // switch(p->as) { |
174 // case AMOVW: | 176 // case AMOVW: |
175 // case AMOVB: | 177 // case AMOVB: |
176 // case AMOVBU: | 178 // case AMOVBU: |
177 // if(p->from.type == D_OREG && p->from.offset == 0) | 179 // if(p->from.type == D_OREG && p->from.offset == 0) |
178 // xtramodes(r, &p->from); | 180 // xtramodes(r, &p->from); |
(...skipping 789 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
968 return 2; | 970 return 2; |
969 if(p->to.offset&(1<<v->reg)) | 971 if(p->to.offset&(1<<v->reg)) |
970 return 4; | 972 return 4; |
971 return 1; | 973 return 1; |
972 } | 974 } |
973 if(p->to.offset&(1<<v->reg)) | 975 if(p->to.offset&(1<<v->reg)) |
974 return 3; | 976 return 3; |
975 } | 977 } |
976 return 0; | 978 return 0; |
977 | 979 |
978 » case ANOP:» /* read, write */ | 980 » case ANOP:» /* read,, write */ |
979 case AMOVW: | 981 case AMOVW: |
980 case AMOVF: | 982 case AMOVF: |
981 case AMOVD: | 983 case AMOVD: |
982 case AMOVH: | 984 case AMOVH: |
983 case AMOVHU: | 985 case AMOVHU: |
984 case AMOVB: | 986 case AMOVB: |
985 case AMOVBU: | 987 case AMOVBU: |
986 case AMOVDW: | 988 case AMOVDW: |
987 case AMOVWD: | 989 case AMOVWD: |
988 case AMOVFD: | 990 case AMOVFD: |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1040 case AMODU: | 1042 case AMODU: |
1041 case AADDF: | 1043 case AADDF: |
1042 case AADDD: | 1044 case AADDD: |
1043 case ASUBF: | 1045 case ASUBF: |
1044 case ASUBD: | 1046 case ASUBD: |
1045 case AMULF: | 1047 case AMULF: |
1046 case AMULD: | 1048 case AMULD: |
1047 case ADIVF: | 1049 case ADIVF: |
1048 case ADIVD: | 1050 case ADIVD: |
1049 | 1051 |
1050 » case ACMPF: | 1052 » case ACMPF:» /* read, read, */ |
1051 case ACMPD: | 1053 case ACMPD: |
1052 case ATST: | |
1053 case ACMP: | 1054 case ACMP: |
1054 case ACMN: | 1055 case ACMN: |
1055 case ACASE: | 1056 case ACASE: |
| 1057 case ATST: /* read,, */ |
1056 if(s != A) { | 1058 if(s != A) { |
1057 if(copysub(&p->from, v, s, 1)) | 1059 if(copysub(&p->from, v, s, 1)) |
1058 return 1; | 1060 return 1; |
1059 if(copysub1(p, v, s, 1)) | 1061 if(copysub1(p, v, s, 1)) |
1060 return 1; | 1062 return 1; |
1061 if(!copyas(&p->to, v)) | 1063 if(!copyas(&p->to, v)) |
1062 if(copysub(&p->to, v, s, 1)) | 1064 if(copysub(&p->to, v, s, 1)) |
1063 return 1; | 1065 return 1; |
1064 return 0; | 1066 return 0; |
1065 } | 1067 } |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1147 | 1149 |
1148 case ATEXT: /* funny */ | 1150 case ATEXT: /* funny */ |
1149 if(v->type == D_REG) | 1151 if(v->type == D_REG) |
1150 if(v->reg == REGARG) | 1152 if(v->reg == REGARG) |
1151 return 3; | 1153 return 3; |
1152 return 0; | 1154 return 0; |
1153 } | 1155 } |
1154 return 0; | 1156 return 0; |
1155 } | 1157 } |
1156 | 1158 |
1157 int | |
1158 a2type(Prog *p) | |
1159 { | |
1160 | |
1161 switch(p->as) { | |
1162 | |
1163 case ATST: | |
1164 case ACMP: | |
1165 case ACMN: | |
1166 | |
1167 case AMULLU: | |
1168 case AMULA: | |
1169 | |
1170 case AADD: | |
1171 case ASUB: | |
1172 case ARSB: | |
1173 case ASLL: | |
1174 case ASRL: | |
1175 case ASRA: | |
1176 case AORR: | |
1177 case AAND: | |
1178 case AEOR: | |
1179 // case AMVN: | |
1180 case AMUL: | |
1181 case AMULU: | |
1182 case ADIV: | |
1183 case ADIVU: | |
1184 case AMOD: | |
1185 case AMODU: | |
1186 return D_REG; | |
1187 | |
1188 case ACMPF: | |
1189 case ACMPD: | |
1190 | |
1191 case AADDF: | |
1192 case AADDD: | |
1193 case ASUBF: | |
1194 case ASUBD: | |
1195 case AMULF: | |
1196 case AMULD: | |
1197 case ADIVF: | |
1198 case ADIVD: | |
1199 return D_FREG; | |
1200 } | |
1201 return D_NONE; | |
1202 } | |
1203 | |
1204 /* | 1159 /* |
1205 * direct reference, | 1160 * direct reference, |
1206 * could be set/use depending on | 1161 * could be set/use depending on |
1207 * semantics | 1162 * semantics |
1208 */ | 1163 */ |
1209 int | 1164 int |
1210 copyas(Adr *a, Adr *v) | 1165 copyas(Adr *a, Adr *v) |
1211 { | 1166 { |
1212 | 1167 |
1213 if(regtyp(v)) { | 1168 if(regtyp(v)) { |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1253 if(a->type == D_SHIFT) { | 1208 if(a->type == D_SHIFT) { |
1254 if((a->offset&0xf) == v->reg) | 1209 if((a->offset&0xf) == v->reg) |
1255 return 1; | 1210 return 1; |
1256 if((a->offset&(1<<4)) && (a->offset>>8) == v->reg) | 1211 if((a->offset&(1<<4)) && (a->offset>>8) == v->reg) |
1257 return 1; | 1212 return 1; |
1258 } | 1213 } |
1259 } | 1214 } |
1260 return 0; | 1215 return 0; |
1261 } | 1216 } |
1262 | 1217 |
| 1218 /* |
| 1219 * compare v to the center |
| 1220 * register in p (p->reg) |
| 1221 * the trick is that this |
| 1222 * register might be D_REG |
| 1223 * D_FREG. there are basically |
| 1224 * two cases, |
| 1225 * ADD r,r,r |
| 1226 * CMP r,r, |
| 1227 */ |
1263 int | 1228 int |
1264 copyau1(Prog *p, Adr *v) | 1229 copyau1(Prog *p, Adr *v) |
1265 { | 1230 { |
1266 | 1231 |
1267 » if(regtyp(v)) { | 1232 » if(regtyp(v)) |
1268 » » if(a2type(p) == v->type) | 1233 » if(p->reg == v->reg) { |
1269 » » if(p->reg == v->reg) { | 1234 » » if(p->to.type != D_NONE) { |
1270 » » » if(a2type(p) != v->type) | 1235 » » » if(v->type == p->to.type) |
1271 » » » » print("botch a2type %P\n", p); | 1236 » » » » return 1; |
1272 » » » return 1; | 1237 » » » return 0; |
1273 » » } | 1238 » » } |
| 1239 » » if(p->from.type != D_NONE) { |
| 1240 » » » if(v->type == p->from.type) |
| 1241 » » » » return 1; |
| 1242 » » » return 0; |
| 1243 » » } |
| 1244 » » print("copyau1: cant tell %P\n", p); |
1274 } | 1245 } |
1275 return 0; | 1246 return 0; |
1276 } | 1247 } |
1277 | 1248 |
1278 /* | 1249 /* |
1279 * substitute s for v in a | 1250 * substitute s for v in a |
1280 * return failure to substitute | 1251 * return failure to substitute |
1281 */ | 1252 */ |
1282 int | 1253 int |
1283 copysub(Adr *a, Adr *v, Adr *s, int f) | 1254 copysub(Adr *a, Adr *v, Adr *s, int f) |
(...skipping 192 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1476 Reg *r; | 1447 Reg *r; |
1477 | 1448 |
1478 if(j->len == 0) | 1449 if(j->len == 0) |
1479 return; | 1450 return; |
1480 if(cond == Truecond) | 1451 if(cond == Truecond) |
1481 pred = predinfo[rstart->prog->as - ABEQ].scond; | 1452 pred = predinfo[rstart->prog->as - ABEQ].scond; |
1482 else | 1453 else |
1483 pred = predinfo[rstart->prog->as - ABEQ].notscond; | 1454 pred = predinfo[rstart->prog->as - ABEQ].notscond; |
1484 | 1455 |
1485 for(r = j->start;; r = successor(r)) { | 1456 for(r = j->start;; r = successor(r)) { |
1486 » » if (r->prog->as == AB) { | 1457 » » if(r->prog->as == AB) { |
1487 » » » if (r != j->last || branch == Delbranch) | 1458 » » » if(r != j->last || branch == Delbranch) |
1488 excise(r); | 1459 excise(r); |
1489 else { | 1460 else { |
1490 » » » » if (cond == Truecond) | 1461 » » » » if(cond == Truecond) |
1491 r->prog->as = predinfo[rstart->prog->as
- ABEQ].opcode; | 1462 r->prog->as = predinfo[rstart->prog->as
- ABEQ].opcode; |
1492 else | 1463 else |
1493 r->prog->as = predinfo[rstart->prog->as
- ABEQ].notopcode; | 1464 r->prog->as = predinfo[rstart->prog->as
- ABEQ].notopcode; |
1494 } | 1465 } |
1495 } | 1466 } |
1496 else | 1467 else |
1497 » » if (predicable(r->prog)) | 1468 » » if(predicable(r->prog)) |
1498 r->prog->scond = (r->prog->scond&~C_SCOND)|pred; | 1469 r->prog->scond = (r->prog->scond&~C_SCOND)|pred; |
1499 » » if (r->s1 != r->link) { | 1470 » » if(r->s1 != r->link) { |
1500 r->s1 = r->link; | 1471 r->s1 = r->link; |
1501 r->link->p1 = r; | 1472 r->link->p1 = r; |
1502 } | 1473 } |
1503 » » if (r == j->last) | 1474 » » if(r == j->last) |
1504 break; | 1475 break; |
1505 } | 1476 } |
1506 } | 1477 } |
1507 | 1478 |
1508 void | 1479 void |
1509 predicate(void) | 1480 predicate(void) |
1510 { | 1481 { |
1511 Reg *r; | 1482 Reg *r; |
1512 int t1, t2; | 1483 int t1, t2; |
1513 Joininfo j1, j2; | 1484 Joininfo j1, j2; |
(...skipping 21 matching lines...) Expand all Loading... |
1535 } | 1506 } |
1536 } | 1507 } |
1537 | 1508 |
1538 int | 1509 int |
1539 isdconst(Addr *a) | 1510 isdconst(Addr *a) |
1540 { | 1511 { |
1541 if(a->type == D_CONST && a->reg == NREG) | 1512 if(a->type == D_CONST && a->reg == NREG) |
1542 return 1; | 1513 return 1; |
1543 return 0; | 1514 return 0; |
1544 } | 1515 } |
LEFT | RIGHT |