Quick Search:

View

Revision:
Expand:  
Changeset: MAIN:ragge:20030804091503

Diff

Diff from 1.38 to:

Annotations

Annotate by Age | Author | Mixed | None
/fisheye/browse/pcc/pcc/mip/reader.c

Annotated File View

ragge
1.38
1 /*      $Id: reader.c,v 1.38 2003/08/04 09:15:03 ragge Exp $    */
ragge
1.31
2 /*
3  * Copyright(C) Caldera International Inc. 2001-2002. All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * Redistributions of source code and documentation must retain the above
10  * copyright notice, this list of conditions and the following disclaimer.
11  * Redistributions in binary form must reproduce the above copyright
12  * notice, this list of conditionsand the following disclaimer in the
13  * documentation and/or other materials provided with the distribution.
14  * All advertising materials mentioning features or use of this software
15  * must display the following acknowledgement:
16  *      This product includes software developed or owned by Caldera
17  *      International, Inc.
18  * Neither the name of Caldera International, Inc. nor the names of other
19  * contributors may be used to endorse or promote products derived from
20  * this software without specific prior written permission.
21  *
22  * USE OF THE SOFTWARE PROVIDED FOR UNDER THIS LICENSE BY CALDERA
23  * INTERNATIONAL, INC. AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
24  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
25  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26  * DISCLAIMED.  IN NO EVENT SHALL CALDERA INTERNATIONAL, INC. BE LIABLE
27  * FOR ANY DIRECT, INDIRECT INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30  * HOWEVER CAUSED AND ON ANY THEORY OFLIABILITY, WHETHER IN CONTRACT,
31  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
32  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 
33  * POSSIBILITY OF SUCH DAMAGE.
34  */
ragge
1.1
35
36 # include "pass2.h"
37
38 /*      some storage declarations */
ragge
1.26
39 /*
40  * TODO: re-invent autoincr()/deltest()
41  */
ragge
1.1
42
43 int nrecur;
44 int lflag;
ragge
1.9
45 int x2debug;
ragge
1.1
46 int udebug = 0;
ragge
1.32
47 int ftnno;
ragge
1.1
48
49 NODE *stotree;
50 int stocook;
ragge
1.37
51 static int saving;
ragge
1.1
52
ragge
1.23
53 static struct templst {
54         struct templst *next;
55         int tempnr;
56         int tempoff;
57 } *templst;
58
ragge
1.10
59 int e2print(NODE *pint downint *aint *b);
ragge
1.37
60 void saveip(struct interpass *ip);
61 void deljumps(void);
62 void optdump(struct interpass *ip);
63
ragge
1.26
64
65 #ifdef PCC_DEBUG
66 static void
67 cktree(NODE *p)
68 {
69         if (p->n_op > MAXOP)
70                 cerror("op %d slipped through"p->n_op);
ragge
1.35
71         if (p->n_op == CBRANCH && !logop(p->n_left->n_op))
72                 cerror("not logop branch");
ragge
1.26
73 }
74 #endif
ragge
1.8
75
ragge
1.17
76 static void
ragge
1.2
77 p2compile(NODE *p)
78 {
ragge
1.15
79 #if !defined(MULTIPASS)
80         extern char *ftitle;
81 #endif
ragge
1.1
82
ragge
1.14
83         if (lflag)
84                 lineid(linenoftitle);
85
ragge
1.1
86         /* generate code for the tree p */
ragge
1.26
87 #ifdef PCC_DEBUG
88         walkf(pcktree);
89         if (e2debug)
90                 fwalk(pe2print0);
91 #endif
ragge
1.25
92
ragge
1.1
93 # ifdef MYREADER
94         MYREADER(p);  /* do your own laundering of the input */
95 # endif
96         nrecur = 0;
ragge
1.25
97         codgen(pFOREFF);
ragge
1.1
98         reclaimpRNULL0 );
99         allchk();
ragge
1.2
100 }
ragge
1.1
101
ragge
1.17
102 static void newblock(int myregint aoff);
103 static void epilogue(int regsint autosint retlab);
104
ragge
1.2
105 void
ragge
1.17
106 pass2_compile(struct interpass *ip)
107 {
ragge
1.37
108         if (Oflag) {
109                 if (ip->type == IP_PROLOG)
110                         saving++;
111                 if (saving)
112                         return saveip(ip);
113         }
ragge
1.17
114         switch (ip->type) {
115         case IP_NODE:
116                 p2compile(ip->ip_node);
ragge
1.21
117                 tfree(ip->ip_node);
ragge
1.17
118                 break;
119         case IP_PROLOG:
120                 prologue(ip->ip_regsip->ip_auto);
121                 break;
122         case IP_NEWBLK:
123                 newblock(ip->ip_regsip->ip_auto);
124                 break;
125         case IP_EPILOG:
126                 epilogue(ip->ip_regsip->ip_autoip->ip_retl);
ragge
1.18
127                 break;
128         case IP_LOCCTR:
129                 setlocc(ip->ip_locc);
130                 break;
131         case IP_DEFLAB:
132                 deflab(ip->ip_lbl);
133                 break;
134         case IP_DEFNAM:
135                 defname(ip->ip_nameip->ip_vis);
136                 break;
ragge
1.17
137         default:
138                 cerror("pass2_compile %d"ip->type);
139         }
140 }
141
142 static void
ragge
1.16
143 newblock(int myregint aoff)
ragge
1.2
144 {
ragge
1.1
145         setregs();
ragge
1.2
146 }
ragge
1.1
147
ragge
1.17
148 static void
ragge
1.16
149 epilogue(int regsint autosint retlab)
ragge
1.2
150 {
ragge
1.23
151         templst = NULL;
ragge
1.16
152         eoftn(regsautosretlab);
ragge
1.2
153 }
ragge
1.1
154
ragge
1.2
155 /*
156  * generate the code for p;
157  * order may call codgen recursively
158  * cookie is used to describe the context
159  */
160 void
161 codgen(NODE *pint cookie)
162 {
ragge
1.1
163
ragge
1.8
164         for (;;) {
ragge
1.1
165                 canon(p);  /* creats OREG from * if possible and does sucomp */
166                 stotree = NIL;
ragge
1.30
167 #ifdef PCC_DEBUG
ragge
1.8
168                 if (e2debug) {
169                         printf("store called on:\n");
170                         fwalk(pe2print0);
171                 }
ragge
1.30
172 #endif
ragge
1.1
173                 store(p);
174                 ifstotree==NIL ) break;
175
176                 /* because it's minimal, can do w.o. stores */
177
178                 orderstotreestocook );
ragge
1.2
179         }
ragge
1.1
180         orderpcookie );
ragge
1.2
181 }
ragge
1.1
182
ragge
1.30
183 #ifdef PCC_DEBUG
ragge
1.1
184 char *cnames[] = {
185         "SANY",
186         "SAREG",
187         "STAREG",
188         "SBREG",
189         "STBREG",
190         "SCC",
191         "SNAME",
192         "SCON",
193         "SFLD",
194         "SOREG",
195         "STARNM",
196         "STARREG",
197         "INTEMP",
198         "FORARG",
199         "SWADD",
200         0,
201         };
202
ragge
1.2
203 /*
204  * print a nice-looking description of cookie
205  */
206 void
207 prcook(int cookie)
208 {
ragge
1.1
209         int iflag;
210
211         ifcookie & SPECIAL ){
212                 ifcookie == SZERO ) printf"SZERO" );
213                 else ifcookie == SONE ) printf"SONE" );
214                 else ifcookie == SMONE ) printf"SMONE" );
215                 else printf"SPECIAL+%d"cookie & ~SPECIAL );
216                 return;
217                 }
218
219         flag = 0;
220         fori=0cnames[i]; ++i ){
221                 ifcookie & (1<<i) ){
222                         ifflag ) printf"|" );
223                         ++flag;
224                         printfcnames[i] );
225                         }
226                 }
227
ragge
1.2
228 }
ragge
1.30
229 #endif
ragge
1.1
230
231 int odebug = 0;
232
ragge
1.2
233 void
234 order(NODE *pint cook)
235 {
236         int otym;
ragge
1.1
237         int cookie;
ragge
1.2
238         NODE *p1, *p2;
ragge
1.1
239
ragge
1.8
240         /*
241          * by this time, p should be able to be generated without stores;
242          * the only question is how
243          */
ragge
1.1
244         again:
245
ragge
1.13
246         if (p->n_op == FREE)
ragge
1.19
247                 cerror("order");        /* whole tree was done */
ragge
1.1
248         cookie = cook;
249         rcount();
250         canon(p);
ragge
1.13
251         rallo(pp->n_rall);
ragge
1.1
252
ragge
1.30
253 #ifdef PCC_DEBUG
ragge
1.8
254         if (odebug) {
255                 printf("order(%p, "p);
256                 prcook(cookie);
257                 printf(")\n");
258                 fwalk(pe2print0);
259         }
ragge
1.30
260 #endif
ragge
1.1
261
ragge
1.13
262         o = p->n_op;
ragge
1.1
263         ty = optype(o);
264
265         /* first of all, for most ops, see if it is in the table */
266
267         /* look for ops */
268
ragge
1.13
269         switch (m = p->n_op) {
ragge
1.1
270
271         default:
272                 /* look for op in table */
ragge
1.8
273                 for (;;) {
274                         if ((m = match(pcookie)) == MDONE)
275                                 goto cleanup;
276                         else if (m == MNOPE) {
277                                 if (!(cookie = nextcook(pcookie)))
278                                         goto nomat;
ragge
1.1
279                                 continue;
ragge
1.8
280                         } else
281                                 break;
282                 }
ragge
1.1
283                 break;
284
285         case FORCE:
286         case CBRANCH:
287         case UNARY CALL:
288         case CALL:
289         case UNARY STCALL:
290         case STCALL:
291         case UNARY FORTCALL:
292         case FORTCALL:
293                 /* don't even go near the table... */
294                 ;
295
ragge
1.8
296         }
ragge
1.25
297         /*
ragge
1.8
298          * get here to do rewriting if no match or
299          * fall through from above for hard ops
300          */
ragge
1.1
301
ragge
1.13
302         p1 = p->n_left;
ragge
1.8
303         if (ty == BITYPE)
ragge
1.13
304                 p2 = p->n_right;
ragge
1.8
305         else
306                 p2 = NIL;
ragge
1.1
307         
ragge
1.30
308 #ifdef PCC_DEBUG
ragge
1.8
309         if (odebug) {
310                 printf("order(%p, "p);
311                 prcook(cook);
312                 printf("), cookie ");
313                 prcook(cookie);
314                 printf(", rewrite %s\n"opst[m]);
315         }
ragge
1.30
316 #endif
ragge
1.8
317         switch (m) {
ragge
1.1
318         default:
319                 nomat:
ragge
1.13
320                 cerror"no table entry for op %s"opst[p->n_op] );
ragge
1.1
321
322         case FORCE:
323                 cook = INTAREG|INTBREG;
ragge
1.19
324                 order(p->n_leftcook);
325                 reclaim(pRLEFTcook);
ragge
1.38
326                 return;
ragge
1.1
327
328         case CBRANCH:
ragge
1.36
329                 p1->n_label = p2->n_lval;
330                 codgen(p1FORCC);
331                 reclaim(p1RNULL0);
ragge
1.19
332                 nfree(p2);
333                 nfree(p);
ragge
1.1
334                 return;
335
336         case FLD:       /* fields of funny type */
ragge
1.13
337                 if ( p1->n_op == UNARY MUL ){
338                         offstarp1->n_left );
ragge
1.1
339                         goto again;
340                         }
341
342         case UNARY MINUS:
ragge
1.30
343                 orderp1INBREG|INAREG);
ragge
1.1
344                 goto again;
345
346         case NAME:
347                 /* all leaves end up here ... */
348                 ifo == REG ) goto nomat;
349                 orderpINTAREG|INTBREG );
350                 goto again;
351
352         case INIT:
ragge
1.12
353                 uerror("init: illegal initialization");
ragge
1.1
354                 return;
355
356         case UNARY FORTCALL:
ragge
1.13
357                 p->n_right = NIL;
ragge
1.1
358         case FORTCALL:
ragge
1.13
359                 o = p->n_op = UNARY FORTCALL;
ragge
1.1
360                 ifgenfcallpcookie ) ) goto nomat;
361                 goto cleanup;
362
363         case UNARY CALL:
ragge
1.13
364                 p->n_right = NIL;
ragge
1.1
365         case CALL:
ragge
1.13
366                 o = p->n_op = UNARY CALL;
ragge
1.1
367                 ifgencallpcookie ) ) goto nomat;
368                 goto cleanup;
369
370         case UNARY STCALL:
ragge
1.13
371                 p->n_right = NIL;
ragge
1.1
372         case STCALL:
ragge
1.13
373                 o = p->n_op = UNARY STCALL;
ragge
1.1
374                 ifgenscallpcookie ) ) goto nomat;
375                 goto cleanup;
376
377                 /* if arguments are passed in register, care must be taken that reclaim
ragge
1.2
378                  * not throw away the register which now has the result... */
ragge
1.1
379
380         case UNARY MUL:
381                 ifcook == FOREFF ){
382                         /* do nothing */
ragge
1.13
383                         orderp->n_leftFOREFF );
ragge
1.19
384                         nfree(p);
ragge
1.1
385                         return;
ragge
1.19
386                 }
ragge
1.30
387                 offstarp->n_left );
388 #if 0
389                 canon(p);
390                 ifcanaddr(p) && cook != INTEMP )
391                         goto cleanup;
ragge
1.1
392 #endif
393                 goto again;
394
395         case INCR:  /* INCR and DECR */
396                 ifsetincr(p) ) goto again;
397
398                 /* x++ becomes (x += 1) -1; */
399
400                 ifcook & FOREFF ){  /* result not needed so inc or dec and be done with it */
401                         /* x++ => x += 1 */
ragge
1.13
402                         p->n_op = (p->n_op==INCR)?ASG PLUS:ASG MINUS;
ragge
1.1
403                         goto again;
404                         }
405
406                 p1 = tcopy(p);
ragge
1.13
407                 reclaimp->n_leftRNULL0 );
408                 p->n_left = p1;
409                 p1->n_op = (p->n_op==INCR)?ASG PLUS:ASG MINUS;
410                 p->n_op = (p->n_op==INCR)?MINUS:PLUS;
ragge
1.1
411                 goto again;
412
413         case STASG:
414                 ifsetstrp ) ) goto again;
415                 goto nomat;
416
417         case ASG PLUS:  /* and other assignment ops */
418                 ifsetasop(p) ) goto again;
419
420                 /* there are assumed to be no side effects in LHS */
421
422                 p2 = tcopy(p);
ragge
1.13
423                 p->n_op = ASSIGN;
424                 reclaimp->n_rightRNULL0 );
425                 p->n_right = p2;
ragge
1.1
426                 canon(p);
ragge
1.13
427                 rallopp->n_rall );
ragge
1.1
428
ragge
1.30
429 #ifdef PCC_DEBUG
ragge
1.8
430                 ifodebug ) fwalkpe2print0 );
ragge
1.30
431 #endif
ragge
1.1
432
ragge
1.13
433                 orderp2->n_leftINTBREG|INTAREG );
ragge
1.1
434                 orderp2INTBREG|INTAREG );
435                 goto again;
436
437         case ASSIGN:
ragge
1.8
438                 if (setasg(p))
439                         goto again;
ragge
1.1
440                 goto nomat;
441
442
443         case BITYPE:
444                 ifsetbinp ) ) goto again;
445                 /* try to replace binary ops by =ops */
446                 switch(o){
447
448                 case PLUS:
449                 case MINUS:
450                 case MUL:
451                 case DIV:
452                 case MOD:
453                 case AND:
454                 case OR:
455                 case ER:
456                 case LS:
457                 case RS:
ragge
1.13
458                         p->n_op = ASG o;
ragge
1.1
459                         goto again;
460                         }
461                 goto nomat;
462
463                 }
464
465         cleanup:
466
467         /* if it is not yet in the right state, put it there */
468
469         ifcook & FOREFF ){
470                 reclaimpRNULL0 );
471                 return;
472                 }
473
ragge
1.13
474         ifp->n_op==FREE ) return;
ragge
1.1
475
476         iftshapepcook ) ) return;
477
478         if( (m=match(p,cook) ) == MDONE ) return;
479
480         /* we are in bad shape, try one last chance */
ragge
1.8
481         if (lastchance(pcook))
482                 goto again;
ragge
1.1
483
484         goto nomat;
ragge
1.8
485 }
ragge
1.1
486
487 int callflag;
488 int fregs;
489
ragge
1.2
490 void
491 storep ) NODE *p; {
ragge
1.1
492
493         /* find a subtree of p which should be stored */
494
ragge
1.2
495         int oty;
ragge
1.1
496
ragge
1.13
497         o = p->n_op;
ragge
1.1
498         ty = optype(o);
499
500         ifty == LTYPE ) return;
501
502         switcho ){
503
504         case UNARY CALL:
505         case UNARY FORTCALL:
506         case UNARY STCALL:
507                 ++callflag;
508                 break;
509
510         case UNARY MUL:
ragge
1.13
511                 if (asgop(p->n_left->n_op))
512                         stoasg(p->n_leftUNARY MUL);
ragge
1.1
513                 break;
514
515         case CALL:
516         case FORTCALL:
517         case STCALL:
ragge
1.13
518                 storep->n_left );
519                 stoargp->n_righto );
ragge
1.1
520                 ++callflag;
521                 return;
522
523         case CBRANCH:   /* to prevent complicated expressions on the LHS from being stored */
ragge
1.13
524                 constorep->n_left );
ragge
1.1
525                 return;
526
527                 }
528
ragge
1.11
529         if (ty == UTYPE) {
ragge
1.13
530                 store(p->n_left);
ragge
1.1
531                 return;
ragge
1.11
532         }
ragge
1.1
533
ragge
1.13
534         if (asgop(p->n_right->n_op))
535                 stoasg(p->n_righto);
ragge
1.1
536
ragge
1.13
537         ifp->n_su>fregs ){ /* must store */
ragge
1.1
538                 mkadrsp );  /* set up stotree and stocook to subtree
539                                  that must be stored */
540                 }
541
ragge
1.13
542         storep->n_right );
543         storep->n_left );
ragge
1.1
544         }
545
ragge
1.2
546 /*
547  * store conditional expressions
548  * the point is, avoid storing expressions in conditional
549  * conditional context, since the evaluation order is predetermined
550  */
551 void
552 constore(NODE *p)
553 {
ragge
1.1
554         storep );
ragge
1.2
555 }
ragge
1.1
556
ragge
1.2
557 /* mark off calls below the current node */
558 void
559 markcall(NODE *p)
560 {
ragge
1.1
561
562         again:
ragge
1.13
563         switchp->n_op ){
ragge
1.1
564
565         case UNARY CALL:
566         case UNARY STCALL:
567         case UNARY FORTCALL:
568         case CALL:
569         case STCALL:
570         case FORTCALL:
571                 ++callflag;
572                 return;
573
574                 }
575
ragge
1.13
576         switchoptypep->n_op ) ){
ragge
1.1
577
578         case BITYPE:
ragge
1.13
579                 markcallp->n_right );
ragge
1.1
580         case UTYPE:
ragge
1.13
581                 p = p->n_left;
ragge
1.1
582                 /* eliminate recursion (aren't I clever...) */
583                 goto again;
584         case LTYPE:
585                 return;
586                 }
587
ragge
1.2
588 }
ragge
1.1
589
ragge
1.2
590 void
591 stoarg(NODE *pint calltype)
592 {
ragge
1.1
593         /* arrange to store the args */
ragge
1.13
594         ifp->n_op == CM ){
595                 stoargp->n_leftcalltype );
596                 p = p->n_right ;
ragge
1.1
597                 }
598         ifcalltype == CALL ){
599                 STOARG(p);
600                 }
601         else ifcalltype == STCALL ){
602                 STOSTARG(p);
603                 }
604         else {
605                 STOFARG(p);
606                 }
607         callflag = 0;
608         store(p);
ragge
1.30
609 #ifdef NO_NESTCALLS
ragge
1.1
610         ifcallflag ){ /* prevent two calls from being active at once  */
611                 SETSTO(p,INTEMP);
612                 store(p); /* do again to preserve bottom up nature....  */
ragge
1.2
613         }
ragge
1.1
614 #endif
ragge
1.2
615 }
ragge
1.1
616
617 int negrel[] = { NEEQGTGELTLEUGTUGEULTULE } ;  /* negatives of relationals */
618
ragge
1.2
619 void
620 rcount()
621 /* count recursions */
ragge
1.1
622         if( ++nrecur > NRECUR ){
623                 cerror"expression causes compiler loop: try simplifying" );
624         }
ragge
1.2
625 }
ragge
1.1
626
ragge
1.30
627 #ifdef PCC_DEBUG
ragge
1.2
628 int
ragge
1.8
629 e2print(NODE *pint downint *aint *b)
ragge
1.2
630 {
ragge
1.1
631
632         *a = *b = down+1;
633         whiledown >= 2 ){
634                 printf"\t" );
635                 down -= 2;
636                 }
637         ifdown-- ) printf"    " );
638
639
ragge
1.13
640         printf"%p) %s"popst[p->n_op] );
641         switchp->n_op ) { /* special cases */
ragge
1.1
642
643         case REG:
ragge
1.13
644                 printf" %s"rnames[p->n_rval] );
ragge
1.1
645                 break;
646
ragge
1.23
647         case TEMP:
648                 printf(" %d", (int)p->n_lval);
649                 break;
650
ragge
1.1
651         case ICON:
652         case NAME:
653         case OREG:
654                 printf" " );
655                 adrputp );
656                 break;
657
658         case STCALL:
659         case UNARY STCALL:
660         case STARG:
661         case STASG:
ragge
1.13
662                 printf" size=%d"p->n_stsize );
663                 printf" align=%d"p->n_stalign );
ragge
1.1
664                 break;
665                 }
666
667         printf", " );
ragge
1.33
668         tprintp->n_typep->n_qual);
ragge
1.1
669         printf", " );
ragge
1.13
670         ifp->n_rall == NOPREF ) printf"NOPREF" );
ragge
1.1
671         else {
ragge
1.13
672                 ifp->n_rall & MUSTDO ) printf"MUSTDO " );
ragge
1.1
673                 else printf"PREF " );
ragge
1.13
674                 printf"%s"rnames[p->n_rall&~MUSTDO]);
ragge
1.1
675                 }
ragge
1.13
676         printf", SU= %d\n"p->n_su );
ragge
1.2
677         return 0;
678 }
ragge
1.30
679 #endif
ragge
1.1
680
681 #ifndef FIELDOPS
ragge
1.7
682 /*
683  * do this if there is no special hardware support for fields
684  */
685 static int
686 ffld(NODE *pint downint *down1int *down2 )
687 {
688         /*
689          * look for fields that are not in an lvalue context,
690          * and rewrite them...
691          */
692         NODE *shp;
693         int sovty;
ragge
1.1
694
ragge
1.13
695         *down1 =  asgopp->n_op );
ragge
1.1
696         *down2 = 0;
697
ragge
1.13
698         if( !down && p->n_op == FLD ){ /* rewrite the node */
ragge
1.1
699
ragge
1.7
700                 if( !rewfld(p) ) return 0;
ragge
1.1
701
ragge
1.13
702                 ty = (szty(p->n_type) == 2)? LONGINT;
703                 v = p->n_rval;
ragge
1.1
704                 s = UPKFSZ(v);
705 # ifdef RTOLBYTES
706                 o = UPKFOFF(v);  /* amount to shift */
707 # else
ragge
1.13
708                 o = szty(p->n_type)*SZINT - s - UPKFOFF(v);  /* amount to shift */
ragge
1.1
709 #endif
710
711                 /* make & mask part */
712
ragge
1.13
713                 p->n_left->n_type = ty;
ragge
1.1
714
ragge
1.13
715                 p->n_op = AND;
716                 p->n_right = talloc();
717                 p->n_right->n_op = ICON;
718                 p->n_right->n_rall = NOPREF;
719                 p->n_right->n_type = ty;
720                 p->n_right->n_lval = 1;
721                 p->n_right->n_rval = 0;
722                 p->n_right->n_name = "";
723                 p->n_right->n_lval <<= s;
724                 p->n_right->n_lval--;
ragge
1.1
725
726                 /* now, if a shift is needed, do it */
727
728                 ifo != 0 ){
729                         shp = talloc();
ragge
1.13
730                         shp->n_op = RS;
731                         shp->n_rall = NOPREF;
732                         shp->n_type = ty;
733                         shp->n_left = p->n_left;
734                         shp->n_right = talloc();
735                         shp->n_right->n_op = ICON;
736                         shp->n_right->n_rall = NOPREF;
737                         shp->n_right->n_type = ty;
738                         shp->n_right->n_rval = 0;
739                         shp->n_right->n_lval = o;  /* amount to shift */
740                         shp->n_right->n_name = "";
741                         p->n_left = shp;
ragge
1.1
742                         /* whew! */
743                 }
744         }
ragge
1.7
745         return 0;
746 }
ragge
1.1
747 #endif
748
ragge
1.23
749 /*
750  * change left TEMPs into OREGs
751  * look for situations where we can turn * into OREG
752  */
ragge
1.2
753 void
754 oreg2(NODE *p)
755 {
ragge
1.1
756
757         NODE *q;
ragge
1.2
758         int r;
759         char *cp;
760         NODE *ql, *qr;
ragge
1.1
761         CONSZ temp;
ragge
1.23
762
763         /*
764          * the size of a TEMP is on multiples of the reg size.
765          */
766         if (p->n_op == TEMP) {
767                 struct templst *w = templst;
768                 p->n_op = OREG;
769                 p->n_rval = FPREG;
770                 while (w != NULL) {
771                         if (w->tempnr == p->n_lval)
772                                 break;
773                         w = w->next;
774                 }
775                 if (w == NULL) {
776                         w = tmpalloc(sizeof(struct templst));
777                         w->tempnr = p->n_lval;
778                         w->tempoff = BITOOR(freetemp(szty(p->n_type)));
779                         w->next = templst;
780                         templst = w;
781                 }
782                 p->n_lval = w->tempoff;
783                 p->n_name = "";
784                 return;
785         }
ragge
1.1
786
ragge
1.13
787         if (p->n_op == UNARY MUL) {
788                 q = p->n_left;
789                 if (q->n_op == REG) {
790                         temp = q->n_lval;
791                         r = q->n_rval;
792                         cp = q->n_name;
ragge
1.1
793                         goto ormake;
ragge
1.12
794                 }
ragge
1.1
795
ragge
1.13
796                 if (q->n_op != PLUS && q->n_op != MINUS)
ragge
1.12
797                         return;
ragge
1.13
798                 ql = q->n_left;
799                 qr = q->n_right;
ragge
1.1
800
801 #ifdef R2REGS
802
803                 /* look for doubly indexed expressions */
804
ragge
1.13
805                 ifq->n_op == PLUS) {
ragge
1.7
806                         int i;
ragge
1.1
807                         if( (r=base(ql))>=0 && (i=offset(qrtlen(p)))>=0) {
808                                 makeor2(pqlri);
809                                 return;
ragge
1.12
810                         } else if((r=base(qr))>=0 && (i=offset(qltlen(p)))>=0) {
ragge
1.1
811                                 makeor2(pqrri);
812                                 return;
813                         }
ragge
1.12
814                 }
ragge
1.1
815
816
817 #endif
818
ragge
1.13
819                 if( (q->n_op==PLUS || q->n_op==MINUS) && qr->n_op == ICON &&
820                                 ql->n_op==REG && szty(qr->n_type)==1) {
821                         temp = qr->n_lval;
822                         ifq->n_op == MINUS ) temp = -temp;
823                         r = ql->n_rval;
824                         temp += ql->n_lval;
825                         cp = qr->n_name;
826                         if( *cp && ( q->n_op == MINUS || *ql->n_name ) ) return;
827                         if( !*cp ) cp = ql->n_name;
ragge
1.1
828
829                         ormake:
ragge
1.13
830                         ifnotoffp->n_typertempcp ) ) return;
831                         p->n_op = OREG;
832                         p->n_rval = r;
833                         p->n_lval = temp;
834                         p->n_name = cp;
ragge
1.1
835                         tfree(q);
836                         return;
837                 }
838         }
ragge
1.12
839 }
ragge
1.1
840
ragge
1.2
841 void
ragge
1.1
842 canon(pNODE *p; {
843         /* put p in canonical form */
844
845 #ifndef FIELDOPS
846         fwalkpffld0 ); /* look for field operators */
847 # endif
848         walkfporeg2 );  /* look for and create OREG nodes */
849 #ifdef MYCANON
850         MYCANON(p);  /* your own canonicalization routine(s) */
851 #endif
852         walkfpsucomp );  /* do the Sethi-Ullman computation */
853
ragge
1.2
854 }
ragge
1.1
855
ragge
1.37
856 static SIMPLEQ_HEAD(, interpassipole = SIMPLEQ_HEAD_INITIALIZER(ipole);
857
858 void
859 saveip(struct interpass *ip)
860 {
861         SIMPLEQ_INSERT_TAIL(&ipoleipsqelem);
862
863         if (ip->type != IP_EPILOG)
864                 return;
865         saving = -1;
866
867         deljumps();
868
869         while ((ip = SIMPLEQ_FIRST(&ipole))) {
870                 SIMPLEQ_REMOVE_HEAD(&ipolesqelem);
871                 pass2_compile(ip);
872         }
873 }
874
875 void
876 deljumps()
877 {
878         struct interpass *ip, *n;
879         int gotone;
880
881 again:  gotone = 0;
882
883         SIMPLEQ_FOREACH(ip, &ipolesqelem) {
884                 if (ip->type == IP_EPILOG)
885                         return;
886                 if (ip->type != IP_NODE)
887                         continue;
888                 if (ip->ip_node->n_op != GOTO)
889                         continue;
890                 n = ip->sqelem.sqe_next;
891                 switch (n->type) {
892                 case IP_NODE:
893                         tfree(n->ip_node);
894                         ip->sqelem.sqe_next = n->sqelem.sqe_next;
895                         break;
896                 case IP_DEFLAB:
897                         if (ip->ip_node->n_left->n_lval != n->ip_lbl)
898                                 continue;
899                         tfree(ip->ip_node);
900                         *ip = *n;
901                         break;
902                 default:
903                         continue;
904                 }
905                 gotone = 1;
906         }
907         if (gotone)
908                 goto again;
909 }
910
911 void
912 optdump(struct interpass *ip)
913 {
914         static char *nm[] = { "node""prolog""newblk""epilog""locctr",
915                 "deflab""defnam" };
916         printf("type %s\n"nm[ip->type-1]);
917         switch (ip->type) {
918         case IP_NODE:
919                 fwalk(ip->ip_nodee2print0);
920                 break;
921         case IP_DEFLAB:
922                 printf("label" LABFMT "\n"ip->ip_lbl);
923                 break;
924         }
925 }
FishEye: Open Source License registered to PCC.
Your maintenance has expired. You can renew your license at http://www.atlassian.com/fisheye/renew
Atlassian FishEye, CVS analysis. (Version:1.6.3 Build:build-336 2008-11-04) - Administration - Page generated 2014-08-23 19:21 +0200