Research V3 development
[unix-history] / c / c10.c
CommitLineData
ca82b6dc
DR
1/*
2
3 C compiler, part 2
4
5 Copyright 1972 Bell Telephone Laboratories, Inc.
6
7*/
8
9waste() /* waste space */
10{
11 waste(waste(waste),waste(waste),waste(waste));
12 waste(waste(waste),waste(waste),waste(waste));
13 waste(waste(waste),waste(waste),waste(waste));
14 waste(waste(waste),waste(waste),waste(waste));
15 waste(waste(waste),waste(waste),waste(waste));
16 waste(waste(waste),waste(waste),waste(waste));
17 waste(waste(waste),waste(waste),waste(waste));
18 waste(waste(waste),waste(waste),waste(waste));
19}
20main(argc, argv)
21char argv[][];
22{
23 extern fout, fin, nerror, line;
24 extern getwrd, rcexpr, tmpfil;
25 extern cctab[], regtab[], efftab[], sptab[];
26 int sp[], c, table[], tabtab[3][], tree;
27
28 if (argc<4) {
29 error("Arg count");
30 exit(1);
31 }
32 if((fin=open(argv[1],0))<0) {
33 error("Cant't find %s", argv[1]);
34 exit(1);
35 }
36 if((fout=creat(argv[3],017))<0) {
37 error("Can't create %s", argv[3]);
38 exit(1);
39 }
40 tmpfil = argv[2];
41
42 tabtab[0] = regtab;
43 tabtab[1] = efftab;
44 tabtab[2] = cctab;
45 tabtab[3] = sptab;
46 while(c=getchar()) {
47 if(c=='#') {
48 sp = 0;
49 c = getwrd();
50 tree = getwrd();
51 table = tabtab[getwrd()];
52 line = getwrd();
53 while(c--)
54 *sp++ = getwrd();
55 rcexpr(tree, table, 0);
56 } else
57 putchar(c);
58 }
59 flush();
60 exit(nerror!=0);
61}
62
63match(tree, table, nreg)
64int tree[], table[]; {
65 extern opdope[], cctab, maprel;
66 int op, d1, d2, t1, t2, p1[], p2[], dope, cctab[];
67 int maprel[];
68 char mp[];
69
70 if (tree==0)
71 return(0);
72 op = *tree;
73 if (op>=29) /* if not leaf */
74 p1 = tree[3];
75 else
76 p1 = tree;
77 t1 = p1[1];
78 d1 = dcalc(p1, nreg);
79 if (((dope=opdope[op])&01)!=0) { /* binary? */
80 p2 = tree[4];
81 t2 = p2[1];
82 d2 = dcalc(p2, nreg);
83 if (d2>d1 & (dope&0100)!=0) /* commute? */
84 if (table!=cctab | (op!=47&op!=48)) { /* commute? */
85 if ((dope&04)!=0) /* relation? */
86 *tree = op = maprel[op-60];
87 dope = t1;
88 t1 = t2;
89 t2 = dope;
90 dope = p1;
91 tree[3] = p1 = p2;
92 tree[4] = p2 = dope;
93 dope = d1;
94 d1 = d2;
95 d2 = dope;
96 dope = t1;
97 t1 = t2;
98 t2 = dope;
99 }
100 }
101 while(*table) {
102 if (*table++ == op) goto foundop;
103 table++;
104 }
105 return(0);
106foundop:
107 table = *table;
108nxtry:
109 mp = table;
110 if (*mp == 0)
111 return(0);
112 if (d1 > (*mp&077) | (*mp>=0100)&(*p1!=36))
113 goto notyet;
114 if (notcompat(t1, mp[1]))
115 goto notyet;
116 if ((opdope[op]&01)!=0 & p2!=0) {
117 if (d2 > (mp[2]&077) | (mp[2]>=0100)&(*p2!=36))
118 goto notyet;
119 if (notcompat(t2,mp[3]))
120 goto notyet;
121 }
122now:
123 return(table[2]);
124notyet:
125 table = table+3;
126 goto nxtry;
127}
128
129rcexpr(tree, table, reg)
130int tree[]; {
131 extern cexpr, regtab, cctab, sptab, printf, error;
132 extern jumpc, cbranch;
133 int r, modf;
134
135 if(tree==0)
136 return(0);
137 if(*tree == 103 | *tree==104) {
138 (*tree==103?jumpc:cbranch)(tree[1],tree[2],tree[3],0);
139 return(0);
140 }
141 modf = isfloat(tree)? 'f':0;
142 if (*tree == 110) { /* force r0 */
143 if((r=rcexpr(tree[3], table, reg)) != 0)
144 printf("mov%c r%d,r0\n", modf, r);
145 return(0);
146 }
147 if ((r=cexpr(tree, table, reg))>=0)
148 return(r);
149 if (table!=regtab)
150 if((r=cexpr(tree, regtab, reg))>=0) {
151 if (table==sptab)
152 printf("mov%c r%d,-(sp)\n", modf, r);
153 if (table==cctab) {
154 if (modf=='f')
155 printf("cfcc\n");
156 printf("tst%c r%d\n", modf, r);
157 }
158 return(0);
159 }
160 error("No match for op %d", *tree);
161}
162
163cexpr(tree, table, reg)
164int tree[][], table[]; {
165 extern match, nreg, printf, pname, putchar, regtab;
166 extern sptab, cctab, rcexpr, prins, rlength, popstk;
167 extern collcon, isn, label, branch, cbranch;
168 extern maprel[];
169 int p1[], p2[], c, r, p[], otable[], ctable[], regtab[], cctab[];
170 int sptab[];
171 char string[], match[];
172 int reg1, rreg;
173
174 if ((c = *tree)==100) { /* call */
175 p1 = tree[3];
176 p2 = tree[4];
177 r = 0;
178 if(*p2) {
179 while (*p2==9) { /* comma */
180 rcexpr(p2[4], sptab, 0);
181 r =+ arlength((p=p2[4])[1]);
182 p2 = p2[3];
183 }
184 rcexpr(p2, sptab, 0);
185 r =+ arlength(p2[1]);
186 }
187 *tree = 101;
188 tree[2] = r; /* save arg length */
189 }
190 if(c==90) { /* ? */
191 cbranch(tree[3], c=isn++, 0, reg);
192 rcexpr(tree[4][3], table, reg);
193 branch(r=isn++, 0);
194 label(c);
195 reg = rcexpr(tree[4][4], table, reg);
196 label(r);
197 goto retrn;
198 }
199 reg = oddreg(tree, reg);
200 reg1 = reg+1;
201 if ((string=match(tree, table, nreg-reg))==0)
202 return(-1);
203 p1 = tree[3];
204 p2 = tree[4];
205loop:
206 switch(c = *string++) {
207
208 case '\0':
209 p = tree;
210 if (*p==101) {
211 if (p[2]>0)
212 popstk(p[2]);
213 reg = 0;
214 }
215retrn:
216 c = isfloat(tree);
217 if (table==cctab & c)
218 printf("cfcc\n");
219 if (!c)
220 if ((c = *tree)==43 | c==73)
221 reg--;
222 return(reg);
223
224 /* A1 */
225 case 'A':
226 p = tree[3];
227 goto adr;
228
229 /* A2 */
230 case 'B':
231 p = tree[4];
232 goto adr;
233
234 /* A */
235 case 'O':
236 p = tree;
237 adr:
238 pname(p);
239 goto loop;
240
241 /* I */
242 case 'M':
243 if ((c = *string)=='\'')
244 string++; else
245 c = 0;
246 prins(*tree, c);
247 goto loop;
248
249 /* B1 */
250 case 'C':
251 if ((c = *tree)<28)
252 p = tree;
253 else
254 p = tree[3];
255 goto pbyte;
256
257 /* BF */
258 case 'P':
259 p = tree;
260 goto pb1;
261
262 /* B2 */
263 case 'D':
264 p = tree[4];
265 pbyte:
266 if (p[1]==1) /* char type? */
267 putchar('b');
268 pb1:
269 if (isfloat(p))
270 putchar('f');
271 goto loop;
272
273 /* BE */
274 case 'L':
275 if (tree[3][1]==1 | tree[4][1]==1)
276 putchar('b');
277 p = tree;
278 goto pb1;
279
280 /* C1 */
281 case 'E':
282 p = p1[3];
283 goto const;
284
285 /* C2 */
286 case 'F':
287 p = p2[3];
288 const:
289 printf("%o", p);
290 goto loop;
291
292 /* F */
293 case 'G':
294 p = p1;
295 goto subtre;
296
297 /* S */
298 case 'K':
299 p = p2;
300 goto subtre;
301
302 /* H */
303 case 'H':
304 p = tree;
305
306 subtre:
307 ctable = regtab;
308 r = reg;
309 c = *string++ - 'A';
310 if ((c&02)!=0)
311 ctable = sptab;
312 if ((c&04)!=0)
313 ctable = cctab;
314 if((c&010)!=0)
315 r = reg1;
316 if((c&01)!=0)
317 if(*p==36) {
318 p = p[3];
319 if(collcon(p) & ctable!=sptab)
320 p = p[3];
321 }
322 rreg = rcexpr(p, ctable, r);
323 if (rreg==r | ctable!=regtab)
324 goto loop;
325 if (string[-2]=='G') /* left operand */
326 if (oddreg(tree, 0)==1) {
327 printf("mov r%d,r%d\n", rreg, r);
328 goto loop;
329 }
330 if (r==reg) {
331 reg = rreg;
332 reg1 = rreg+1;
333 } else
334 reg1 = rreg;
335 goto loop;
336
337 /* R */
338 case 'I':
339 r = reg;
340 if (*string=='-') {
341 string++;
342 r--;
343 }
344 goto preg;
345
346 /* R1 */
347 case 'J':
348 r = reg1;
349 preg:
350 if (r>=5)
351 error("Register overflow: simplify expression");
352 printf("r%d", r);
353 goto loop;
354
355 case '#':
356 p = p1[3];
357 goto nmbr;
358
359 case '"':
360 p = p2[3];
361 goto nmbr;
362
363 case '~':
364 p = tree[3];
365
366 nmbr:
367 if(collcon(p)) {
368 if (*p==41) /* - */
369 putchar('-');
370 switch (*(p = p[4])) {
371
372 case 21: /* number */
373 if (p[3])
374 printf("%d.", p[3]);
375 break;
376
377 case 35: /* & name */
378 pname(p[3]);
379 break;
380
381 }
382 }
383 goto loop;
384
385 /* V */
386 case 'V':
387 tree[0] = maprel[(c=tree[0])-60];
388 goto loop;
389
390 /* Z */
391 case 'Z':
392 printf("$%o", p1[5]+p1[4]);
393 goto loop;
394
395 case '^': /* for ++ -- */
396 printf("%o", tree[4]);
397 goto loop;
398 }
399 putchar(c);
400 goto loop;
401}
402
403pname(p)
404int p[][]; {
405 char np[];
406 int i;
407
408loop:
409 switch(*p) {
410
411 case 21: /* const */
412 printf("$%o", p[3]);
413 return;
414
415 case 23: /* float const */
416 printf("L%d", p[3]);
417 return;
418
419 casename:
420 case 20: /* name */
421 if (i=p[4])
422 printf("%d.+", i);
423 switch(p[3]) {
424
425 case 5: /* auto, param */
426 printf("%d.(r5)", p[5]);
427 return;
428
429 /* extern */
430 case 6:
431 printf("%p", &p[5]);
432 return;
433
434 case 4:
435 error("Illegal structure reference");
436 printf("$0");
437 return;
438
439 }
440 printf("L%d", p[5]);
441 return;
442
443 case 35: /* & */
444 putchar('$');
445 p = p[3];
446 goto loop;
447
448 case 36: /* * */
449 putchar('*');
450 p = p[3];
451 goto loop;
452
453 }
454 error("pname called illegally");
455}
456
457dcalc(p, nreg)
458int p[]; {
459 int op, t, p1[], p2[];
460
461 if (p==0)
462 return(0);
463 op = *p;
464 switch (op) {
465
466 case 20: /* name */
467 case 35: /* & (non-automatic) */
468 return(12);
469
470 case 21: /* short constant */
471 return(p[3]==0? 4:8);
472
473 case 23: /* float const */
474 return(p[3]==0? 4:12);
475
476 case 36: /* * */
477 p1 = p[3];
478 if (*p1==20) /* name or offset name */
479 return(12);
480 }
481
482def:
483 return(p[2]<=nreg? 20: 24);
484}
485
486notcompat(at, st) {
487
488 if (st==0) /* word, byte */
489 return(at>1 & at<=07);
490 if (st==1) /* word */
491 return(at>0 & at<=07);
492 st =- 2;
493 if ((at&077740) != 0)
494 at = 020; /* *int for **stuff */
495 if ((at&077770) != 0)
496 at = at&07 | 020;
497 if (st==2 & at==3)
498 at = 2;
499 return(st != at);
500}
501
502prins(op, c) {
503 extern instab[], printf;
504 int insp[];
505
506 insp = instab;
507 while(*insp) {
508 if (*insp++ == op) {
509 if ((c = insp[c!=0])==0)
510 goto err;
511 printf("%s", c);
512 return;
513 } else
514 insp = insp + 2;
515 }
516err:
517 error("No match' for op %d", op);
518}
519
520collcon(p)
521int p[]; {
522 int p1[], t[];
523
524 if(*p==40 | *p==41) {
525 if(*(p1=p[4])==21) { /* number */
526 return(1);
527 }
528 if (*p1==35)
529 return(1);
530 if (*(p1=p[3])==35) {
531 p1 = p[3];
532 p[3] = p[4];
533 p[4] = p1;
534 return(1);
535 }
536 }
537 return(0);
538}
539
540isfloat(t)
541int t[];
542{
543 extern opdope[];
544 int rt;
545
546 if ((opdope[t[0]]&04)!=0) /* relational */
547 t = t[3];
548 if ((rt=t[1])>=2 & rt<=3)
549 return(rt);
550 return(0);
551}
552
553nreg 3;
554isn 10000;
555namsiz 8;
556line;
557tmpfil;
558nerror;
559
560oddreg(t, reg)
561int t[];
562{
563 if (!isfloat(t))
564 switch(*t) {
565 case 43: /* / */
566 case 44: /* % */
567 case 73: /* =/ */
568 case 74: /* =% */
569 reg++;
570
571 case 42: /* * */
572 case 72: /* =* */
573 return(reg|1);
574 }
575 return(reg);
576}
577
578arlength(t)
579{
580 int arl;
581
582 if ((arl=rlength(t)) == 4)
583 return(8);
584 return(arl);
585}
586
587maprel[] 60, 61, 64, 65, 62, 63, 68, 69, 66, 67;
588