2 * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
3 * See the copyright notice in the ACK home directory, in the file "Copyright".
5 /* #define CODEDEBUG /* print readable code */
7 int code_in_c=0; /* put readable code in "code" */
8 int tabledebug=1; /* generate code for table debugging */
10 int code_in_c=1; /* put code in "tables.c" */
11 int tabledebug=0; /* do not generate code for table debugging */
13 int verbose=0; /* print all statistics */
14 int use_tes; /* use top element size information */
15 char *c_file= "tables.c";
16 char *h_file= "tables.H";
17 char *cd_file= "code";
20 static char rcsid[]= "$Id: output.c,v 0.26 1994/06/24 10:37:52 ceriel Exp $";
48 extern char *l_strings[];
50 extern int ninstances;
51 extern inst_t l_instances[];
54 extern move_t l_moves[];
56 extern test_t l_tests[];
58 extern c1_t l_stacks[];
60 extern c3_t l_coercs[];
61 extern int nsplit,maxsplit;
62 extern c2_t l_split[];
63 extern set_t l_sets[];
69 opnfile(f,s) FILE **f; char *s; {
71 if ((*f=fopen(s,"w"))==NULL)
72 fatal("Can't create %s",s);
75 unlfile(f,s) FILE *f; char *s; {
79 error("%s incorrect, must be removed!!",s);
83 extern char *myalloc();
85 opnfile(&ctable,c_file);
86 opnfile(&htable,h_file);
88 fprintf(ctable,"char coderules[] = {");
90 opnfile(&code,cd_file);
93 lineset = (short *) myalloc(SZOFSET(MAXSOURCELINES)*sizeof(short));
99 fprintf(ctable,"\n};\n\n");
100 fprintf(ctable, "int allsetno = %d;\n", allsetno);
105 if ((fd=creat("lineset",0666))>=0) {
106 sz = SZOFSET(maxline)*2;
107 write(fd,&sz,sizeof(int));
108 write(fd,lineset,sz);
111 error("Can't create lineset");
117 unlfile(ctable,c_file);
118 unlfile(htable,h_file);
120 unlfile(code,cd_file);
124 #define code8(x) fprintf(code,"%s","x")
125 #define code8nl(x) fprintf(code,"%s\n","x")
126 #define code53(x,y) fprintf(code,"%s-%d","x",y)
127 #define codeint(x) fprintf(code," %d",x)
128 #define codenl() fprintf(code,"\n")
131 #define code8nl(x) code8(x)
137 fprintf(ctable,"%d,",x&0377);
149 assert(x>=0 && x<=32767);
161 char pattern[MAXPATBYTES];
165 extern int npatterns;
166 extern int patindex[];
169 extern int empatexpr;
175 prevind = npatbytes-2;
177 for(i=0;i<empatlen;i++)
183 for(i=0;i<npatterns;i++)
189 for (i = 0; i < nprocargs; i++) pat(procarg[i]);
212 NEXT(npatbytes, MAXPATBYTES, "Pattern bytes");
213 pattern[npatbytes]=n;
218 register char *bp,*tp;
220 unsigned short hashvalue;
225 bp = &pattern[index];
230 i |= (*tp++&BMASK)<<BSHIFT;
235 default: /* 3 or more */
236 hashvalue = (hashvalue<<4)^(*tp++&BMASK);
238 hashvalue = (hashvalue<<4)^(*tp++&BMASK);
240 hashvalue = (hashvalue<<4)^(*tp++&BMASK);
242 assert(hashvalue!= ILLHASH);
244 index = (bp[PO_NEXT]&BMASK)|(bp[PO_NEXT+1]<<BSHIFT);
245 bp[PO_HASH] = hashvalue>>BSHIFT;
247 bp[PO_NEXT] = pathash[hashvalue]&BMASK;
248 bp[PO_NEXT+1] = pathash[hashvalue]>>BSHIFT;
249 pathash[hashvalue] = i;
255 fprintf(ctable,"#include \"param.h\"\n");
256 fprintf(ctable,"#include \"tables.h\"\n");
257 fprintf(ctable,"#include \"types.h\"\n");
258 fprintf(ctable,"#include <cgg_cg.h>\n");
259 fprintf(ctable,"#include \"data.h\"\n");
264 short rset[SZOFSET(MAXREGS)];
265 short clashlist[MAXREGS*MAXREGS];
270 fprintf(ctable,"char stregclass[] = {\n");
271 for (i=0;i<nregs;i++)
272 fprintf(ctable,"\t%d,\n",l_regs[i].ri_class);
273 fprintf(ctable,"};\n\nstruct reginfo machregs[] = {\n{0},\n");
274 for (i=1;i<nregs;i++) {
275 fprintf(ctable,"{%d,%d",strlookup(l_regs[i].ri_repr),
278 fprintf(ctable,",{");
279 for(j=0;j<maxmembers;j++)
280 fprintf(ctable,"%d,",l_regs[i].ri_memb[j]);
281 /* now compute and print set of registers
282 * that clashes with this register.
283 * A register clashes with al its children (and theirs)
284 * and with all their parents.
286 for (j=0;j<SZOFSET(MAXREGS);j++)
291 for (j=1;j<nregs;j++)
294 if ((t=l_regs[j].ri_memb[k])!=0) {
302 for (j=1;j<nregs;j++)
304 if ((t=l_regs[j].ri_memb[k])!=0)
311 fprintf(ctable,"},{");
312 for (j=0;j<SZOFSET(nregs);j++)
313 fprintf(ctable,"0%o,",rset[j]&0xFFFF);
314 fprintf(ctable,"}, %d", iclashlist);
315 for (j = 1; j < nregs; j++) {
316 if (BIT(rset, j)) clashlist[iclashlist++] = j;
318 clashlist[iclashlist++] = 0;
320 fprintf(ctable,",%d",l_regs[i].ri_rregvar>=0);
321 fprintf(ctable,"},\n");
323 fprintf(ctable,"};\n\n short clashlist[] = {\n\t");
324 for (i = 0; i < iclashlist; i++) {
325 fprintf(ctable, "%d, ", clashlist[i]);
326 if (clashlist[i] == 0) fprintf(ctable, "\n\t");
328 fprintf(ctable, "0};\n\n");
334 fprintf(htable,"#define REGVARS\n");
335 fprintf(ctable,"#include \"regvar.h\"\n");
336 fprintf(ctable,"int nregvar[4] = { ");
338 fprintf(ctable,"%d, ",nregvar[i]);
339 if (nregvar[i]>maxregvars)
340 maxregvars = nregvar[i];
342 fprintf(ctable,"};\n");
345 fprintf(ctable,"struct regassigned ratar%d[%d];\n",
347 for (i=0;i<4;i++) if (nregvar[i]>0) {
348 fprintf(ctable,"int rvtar%d[] = {",i);
349 for (j=0;j<nregvar[i];j++)
350 fprintf(ctable,"%d,",rvnumbers[i][j]);
351 fprintf(ctable,"};\n");
353 fprintf(ctable,"\nint *rvnumbers[] = {\n");
356 fprintf(ctable,"\trvtar%d,\n",i);
358 fprintf(ctable,"\t0,\n");
359 fprintf(ctable,"};\n\nstruct regassigned *regassigned[] = {\n");
362 fprintf(ctable,"\tratar%d,\n",i);
364 fprintf(ctable,"\t0,\n");
365 fprintf(ctable,"};\n");
371 if (n== -1) return(1);
372 if (n== -2) return(3);
381 fprintf(ctable,"\"");
382 while ((c= (*p++&0377))!=0) {
383 if (! isascii(c) || iscntrl(c)) {
384 fprintf(ctable,"\\%c%c%c",
385 ((c&~0300)>>6) + '0', ((c&070)>>3)+'0',
388 else fprintf(ctable, "%c",c);
390 fprintf(ctable,"\"");
397 fprintf(ctable,"tkdef_t tokens[] = {{0},\n");
398 for (tokno=1;tokno<ntokens;tokno++) {
399 tp = l_tokens[tokno];
400 fprintf(ctable,"/* %3d */{%d,{%d,%d},{", tokno,
401 tp->tk_size, tp->tk_cost.ct_space, tp->tk_cost.ct_time);
402 for(i=0;i<maxtokensize;i++)
403 fprintf(ctable,"%d,",typeconv(tp->tk_att[i].ta_type));
404 fprintf(ctable,"},%d},\t/* ",tp->tk_format);
405 if (tp->tk_format >= 0) outfmt(l_strings[tp->tk_format]);
406 else fprintf(ctable, "(no format)");
407 fprintf(ctable," */\n");
409 fprintf(ctable,"{0}};\n\n");
414 extern node_t nodes[];
417 fprintf(ctable,"node_t enodes[] = {\n");
418 for (np=nodes;np<&nodes[nnodes];np++)
419 fprintf(ctable,"{%d,%d,%d},\n",
420 np->ex_operator,np->ex_lnode,np->ex_rnode);
421 fprintf(ctable,"};\n\n");
428 extern char * filename;
431 fprintf(ctable,"char *tablename = \"%s\";\n",filename);
432 fprintf(ctable,"string codestrings[] = {\n");
433 for(i=0;i<nstrings;i++) {
434 fprintf(ctable,"\t");
435 outfmt(l_strings[i]);
437 while ((c= (*p++&0377))!=0) {
438 if (! isascii(c) || iscntrl(c)) {
439 fprintf(ctable,"\\%c%c%c",
440 ((c&~0300)>>6) + '0', ((c&070)>>3)+'0',
443 else fprintf(ctable, "%c",c);
445 fprintf(ctable,"\",\n");
447 fprintf(ctable,",\n");
449 fprintf(ctable,"};\n\n");
452 extern set_t unstackset;
458 fprintf(ctable,"set_t machsets[] = {\n");
459 for (sp=l_sets;sp< &l_sets[nsets]; sp++) {
460 fprintf(ctable,"/* %3ld */ {%3d,{",(long)(sp-l_sets),sp->set_size);
461 for (i=0;i<setsize;i++)
462 fprintf(ctable,"0x%x,",sp->set_val[i]&0xFFFF);
463 fprintf(ctable,"}},\n");
465 fprintf(ctable,"};\n\n");
467 fprintf(ctable, "set_t unstackset = { %3d,{\n", unstackset.set_size);
468 for (i = 0; i<setsize;i++)
469 fprintf(ctable,"0x%x,",unstackset.set_val[i]&0xFFFF);
470 fprintf(ctable,"}};\n\n");
477 fprintf(ctable,"inst_t tokeninstances[] = {\n");
478 for (ip=l_instances;ip< &l_instances[ninstances]; ip++) {
479 fprintf(ctable,"{ %d, {",ip->in_which);
480 for(i=0;i<=maxtokensize;i++)
481 fprintf(ctable,"%d,",ip->in_info[i]);
482 fprintf(ctable,"}},\n");
484 fprintf(ctable,"};\n\n");
490 fprintf(ctable,"move_t moves[] = {\n");
491 for (mp=l_moves; mp< &l_moves[nmoves]; mp++)
492 fprintf(ctable,"{%d,%d,%d,%d,%d},\n",
493 mp->m_set1, mp->m_expr1,
494 mp->m_set2, mp->m_expr2,
496 fprintf(ctable,"{-1}\n};\n\n");
502 fprintf(ctable,"test_t tests[] = {\n");
503 for (tp=l_tests; tp< &l_tests[ntests]; tp++)
504 fprintf(ctable,"{%d,%d,%d},\n",
505 tp->t_set, tp->t_expr,
507 fprintf(ctable,"{-1}\n};\n\n");
513 fprintf(ctable,"c1_t c1coercs[] = {\n");
514 for (cp=l_stacks; cp< &l_stacks[nstacks]; cp++)
515 fprintf(ctable,"{%d,%d,%d,%d},\n",
516 cp->c1_texpno, cp->c1_expr,
517 cp->c1_prop, cp->c1_codep);
518 fprintf(ctable,"{-1}\n};\n\n");
525 fprintf(ctable,"c2_t c2coercs[] = {\n");
526 for (cp=l_split; cp< &l_split[nsplit]; cp++) {
527 fprintf(ctable,"{%d,%d,%d,{",
528 cp->c2_texpno, cp->c2_expr, cp->c2_nsplit);
529 for (i=0;i<maxsplit;i++)
530 fprintf(ctable,"%d,",cp->c2_repl[i]);
531 fprintf(ctable,"},%d},\n",cp->c2_codep);
533 fprintf(ctable,"{-1}\n};\n\n");
539 fprintf(ctable,"c3_t c3coercs[] = {\n");
540 for (cp=l_coercs; cp< &l_coercs[ncoercs]; cp++)
541 fprintf(ctable,"{%d,%d,%d,%d,%d},\n",
542 cp->c3_texpno, cp->c3_expr,
543 cp->c3_prop, cp->c3_repl, cp->c3_codep);
544 fprintf(ctable,"{-1}\n};\n\n");
551 for(propno=0;propno<nprops;propno++) {
552 fprintf(ctable,"struct reginfo *rlist%d[] = {\n",propno);
553 for(regno=1;regno<nregs;regno++)
554 if (BIT(l_props[propno].pr_regset,regno))
555 fprintf(ctable,"&machregs[%d],\n",regno);
556 fprintf(ctable,"0\n};\n");
558 fprintf(ctable,"struct reginfo **reglist[] = {\n");
559 for(propno=0;propno<nprops;propno++)
560 fprintf(ctable,"rlist%d,\n",propno);
561 fprintf(ctable,"};\n\n");
566 fprintf(ctable,"unsigned cc1 = %u;\n",fc1);
567 fprintf(ctable,"unsigned cc2 = %u;\n",fc2);
568 fprintf(ctable,"unsigned cc3 = %u;\n",fc3);
569 fprintf(ctable,"unsigned cc4 = %u;\n",fc4);
574 fprintf(htable,"#define %s %d\n",s,n);
580 sprintf(buf,"T%s",s);
581 cdef(buf,cmustbeset(s));
585 register symbol *sy_p;
586 extern int maxempatlen,maxrule;
592 if ((sy_p=lookup("FORMAT",symsconst,justlooking))!=0) {
593 wrdfmt = l_strings[sy_p->sy_value.syv_stringno];
594 fprintf(htable,"#define WRD_FMT \"%s\"\n",wrdfmt);
596 cdef("MAXALLREG",maxallreg);
597 cdef("SETSIZE",setsize);
599 cdef("REGSETSIZE",SZOFSET(nregs));
600 cdef("TOKENSIZE",maxtokensize);
601 cdef("MAXMEMBERS",maxmembers);
602 cdef("LONGESTPATTERN",maxempatlen);
603 cdef("MAXPATLEN",maxtokpatlen);
604 cdef("MAXREPLLEN",maxtokrepllen);
605 cdef("MAXEMREPLLEN",maxemrepllen);
606 cdef("MAXPROCARG",maxprocargs);
607 cdef("MAXRULE",maxrule<16 ? 16 : maxrule);
609 cdef("MAXSPLIT",maxsplit);
612 cdef("TABLEDEBUG",1);
621 fprintf(htable,"#define CODEINC 1\n");
623 fprintf(ctable,"char coderules[%d];\n",codeindex);
624 fprintf(ctable,"int ncodebytes=%d;\n",codeindex);
626 fprintf(ctable,"char pattern[%d]={\n",npatbytes+1);
627 for(i=0;i<=npatbytes;i++) {
628 fprintf(ctable,"%d,%c",pattern[i]&BMASK,i%16==15 ? '\n' : ' ');
630 fprintf(ctable,"};\n\n");
631 fprintf(ctable,"int pathash[256]={\n");
633 fprintf(ctable,"%d,%c",pathash[i]&0xFFFF,i%10==9 ? '\n' : ' ');
635 fprintf(ctable,"};\n");
643 setsize = SZOFSET(nregs+ntokens);
674 dopattern(stackcoerc,kills,allocates,generates,yields,leaving)
675 varinfo *kills,*allocates,*generates,*yields,*leaving;
679 register struct varinfo *vp,*vivp;
680 register instr_p instp;
687 static char tlab[] = "0:";
688 extern int optexact,optstack,startline;
689 extern char *filename;
693 fprintf(code,"Code(%d) at \"%s\", line %d\n",stackcoerc,filename,lineno);
696 fprintf(ctable,"\n/* \"%s\", line %d */ ",filename,lineno);
701 if (startline<MAXSOURCELINES) {
702 if (startline>maxline)
704 BIS(lineset,startline);
706 static int beenhere=0;
710 error("Too many source lines for table debug");
718 code53(DO_XXMATCH,tokpatlen);
720 code53(DO_XMATCH,tokpatlen);
722 code53(DO_MATCH,tokpatlen);
723 for (i=0;i<tokpatlen;i++)
724 codeint(tokpatset[i]);
726 } else if (stackcoerc)
729 code53(DO_TOSTACK,0);
734 for (vp=kills;vp!=0;vp=vp->vi_next) {
735 if (vp->vi_int[1] != 0) {
737 codeint(vp->vi_int[0]);
738 codeint(vp->vi_int[1]);
739 } else if (vp->vi_int[0] >= 0) {
741 codeint(vp->vi_int[0]);
744 codeint(-vp->vi_int[0] - 1);
749 for(vp=generates;vp!=0;vp=vp->vi_next) {
750 if (vp->vi_int[0] != INSREMOVE)
752 for(i=0;i<nremoves;i++)
753 if (vp->vi_int[1]==removelist[i])
756 assert(nremoves<(sizeof(removelist)/sizeof(int)));
757 removelist[nremoves++] = vp->vi_int[1];
760 for(i=0;i<nremoves;i++) {
762 codeint(removelist[i]);
767 for (vp=allocates;vp!=0;vp=vp->vi_next) {
768 if (vp->vi_int[0] == -1) { /* Deallocate */
770 code8(DO_DEALLOCATE);
771 codeint(vp->vi_int[1]);
774 if (vp->vi_int[1]==0) {
775 code53(DO_ALLOCATE,0);
776 codeint(vp->vi_int[0]);
779 code53(DO_ALLOCATE,1);
780 codeint(vp->vi_int[0]);
781 codeint(vp->vi_int[1]);
788 code8nl(DO_REALLOCATE);
791 totcost.ct_space = 0;
793 for(vp=generates;vp!=0;vp=vp->vi_next) {
800 code53(DO_INSTR,nops);
801 if (vp->vi_int[1]==0) {
802 codeint(instp->i_asname);
804 codeint(10000+vp->vi_int[1]);
807 for(i=0;i<nops;i++) {
808 codeint(vivp->vi_int[0]);
812 totcost.ct_space += instp->i_cost.ct_space;
813 totcost.ct_time += instp->i_cost.ct_time ;
820 codeint(vp->vi_int[1]);
821 codeint(vp->vi_int[2]);
827 codeint(vp->vi_int[1]);
836 tlab[0] = vp->vi_int[1] + '0';
838 codeint(strlookup(tlab));
842 cocono=vp->vi_int[1];
846 codeint(vp->vi_int[1]);
852 codeint(vp->vi_int[1]);
858 vil = vilength(yields);
859 if (vil!=0 || tokpatlen!=0 || allocates!=0) {
860 code53(DO_TOKREPLACE,vilength(yields));
861 for(vp=yields;vp!=0;vp=vp->vi_next) {
862 codeint(vp->vi_int[0]);
867 code53(DO_EMREPLACE,vilength(leaving));
869 codeint(leaving->vi_int[0]);
870 codeint(leaving->vi_int[1]);
871 leaving = leaving->vi_next;
875 if (totcost.ct_space!=0 || totcost.ct_time!=0) {
877 codeint(totcost.ct_space);
878 codeint(totcost.ct_time);
881 if (empatlen==0 && !inproc)
887 used(resource,use,max) char *resource; {
889 if (verbose || 4*use > 3*max)
890 fprintf(stderr,"%s %d(%d)\n",resource,use,max);
894 extern char *beg_sbrk,*sbrk();
895 extern int nnodes, maxempatlen,maxrule;
897 used("Registers",nregs,MAXREGS);
898 used("Properties",nprops,MAXPROPS);
899 used("Tokens",ntokens,MAXTOKENS);
900 used("Tokensize",maxtokensize,MAXATT);
901 used("Sets",nsets,MAXSETS);
902 used("Instructions",ninstr,MAXINSTR);
903 used("Strings",nstrings,MAXSTRINGS);
904 used("Exp-nodes",nnodes,MAXNODES);
905 used("EM-pat length",maxempatlen,EMPATMAX);
906 used("rules/EM-pattern",maxrule,MAXPATTERNS);
907 used("Allocates/rule",maxallreg,MAXALLREG);
908 used("Instances",ninstances,MAXINSTANCES);
909 used("Moves",nmoves,MAXMOVES);
910 used("Tests",ntests,MAXTESTS);
911 used("Stacks",nstacks,MAXSTACKS);
912 used("1->1 Coercions",ncoercs,MAXCOERCS);
913 used("Splitting coercions",nsplit,MAXSPLCOERC);
914 used("Register variables",maxregvars,MAXREGVAR);
915 used("Pat bytes",npatbytes+1,MAXPATBYTES);
917 used("Source lines",maxline,MAXSOURCELINES);
918 fprintf(stderr,"%ldK heap used\n",((long) (sbrk(0)-beg_sbrk+1023))/1024);