123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612 |
- # include "ldefs.h"
- uchar *
- getl(uchar *p) /* return next line of input, throw away trailing '\n' */
- /* returns 0 if eof is had immediately */
- {
- int c;
- uchar *s, *t;
- t = s = p;
- while(((c = gch()) != 0) && c != '\n')
- *t++ = c;
- *t = 0;
- if(c == 0 && s == t) return((uchar *)0);
- prev = '\n';
- pres = '\n';
- return(s);
- }
- void
- printerr(char *type, char *fmt, va_list argl)
- {
- char buf[1024];
- if(!eof)fprint(errorf,"%d: ",yyline);
- fprint(errorf,"(%s) ", type);
- vseprint(buf, buf+sizeof(buf), fmt, argl);
- fprint(errorf, "%s\n", buf);
- }
- void
- error(char *s,...)
- {
- va_list argl;
- va_start(argl, s);
- printerr("Error", s, argl);
- va_end(argl);
- # ifdef DEBUG
- if(debug && sect != ENDSECTION) {
- sect1dump();
- sect2dump();
- }
- # endif
- if(
- # ifdef DEBUG
- debug ||
- # endif
- report == 1) statistics();
- exits("error"); /* error return code */
- }
- void
- warning(char *s,...)
- {
- va_list argl;
- va_start(argl, s);
- printerr("Warning", s, argl);
- va_end(argl);
- Bflush(&fout);
- }
- void
- lgate(void)
- {
- int fd;
- if (lgatflg) return;
- lgatflg=1;
- if(foutopen == 0){
- fd = create("lex.yy.c", OWRITE, 0666);
- if(fd < 0)
- error("Can't open lex.yy.c");
- Binit(&fout, fd, OWRITE);
- foutopen = 1;
- }
- phead1();
- }
- void
- cclinter(int sw)
- {
- /* sw = 1 ==> ccl */
- int i, j, k;
- int m;
- if(!sw){ /* is NCCL */
- for(i=1;i<NCH;i++)
- symbol[i] ^= 1; /* reverse value */
- }
- for(i=1;i<NCH;i++)
- if(symbol[i]) break;
- if(i >= NCH) return;
- i = cindex[i];
- /* see if ccl is already in our table */
- j = 0;
- if(i){
- for(j=1;j<NCH;j++){
- if((symbol[j] && cindex[j] != i) ||
- (!symbol[j] && cindex[j] == i)) break;
- }
- }
- if(j >= NCH) return; /* already in */
- m = 0;
- k = 0;
- for(i=1;i<NCH;i++)
- if(symbol[i]){
- if(!cindex[i]){
- cindex[i] = ccount;
- symbol[i] = 0;
- m = 1;
- } else k = 1;
- }
- /* m == 1 implies last value of ccount has been used */
- if(m)ccount++;
- if(k == 0) return; /* is now in as ccount wholly */
- /* intersection must be computed */
- for(i=1;i<NCH;i++){
- if(symbol[i]){
- m = 0;
- j = cindex[i]; /* will be non-zero */
- for(k=1;k<NCH;k++){
- if(cindex[k] == j){
- if(symbol[k]) symbol[k] = 0;
- else {
- cindex[k] = ccount;
- m = 1;
- }
- }
- }
- if(m)ccount++;
- }
- }
- }
- int
- usescape(int c)
- {
- int d;
- switch(c){
- case 'n': c = '\n'; break;
- case 'r': c = '\r'; break;
- case 't': c = '\t'; break;
- case 'b': c = '\b'; break;
- case 'f': c = 014; break; /* form feed for ascii */
- case '0': case '1': case '2': case '3':
- case '4': case '5': case '6': case '7':
- c -= '0';
- while('0' <= (d=gch()) && d <= '7'){
- c = c * 8 + (d-'0');
- if(!('0' <= peek && peek <= '7')) break;
- }
- break;
- }
- return(c);
- }
- int
- lookup(uchar *s, uchar **t)
- {
- int i;
- i = 0;
- while(*t){
- if(strcmp((char *)s, *(char **)t) == 0)
- return(i);
- i++;
- t++;
- }
- return(-1);
- }
- int
- cpyact(void)
- { /* copy C action to the next ; or closing } */
- int brac, c, mth;
- int savline, sw;
- brac = 0;
- sw = TRUE;
- savline = 0;
- while(!eof){
- c = gch();
- swt:
- switch( c ){
- case '|': if(brac == 0 && sw == TRUE){
- if(peek == '|')gch(); /* eat up an extra '|' */
- return(0);
- }
- break;
- case ';':
- if( brac == 0 ){
- Bputc(&fout, c);
- Bputc(&fout, '\n');
- return(1);
- }
- break;
- case '{':
- brac++;
- savline=yyline;
- break;
- case '}':
- brac--;
- if( brac == 0 ){
- Bputc(&fout, c);
- Bputc(&fout, '\n');
- return(1);
- }
- break;
- case '/': /* look for comments */
- Bputc(&fout, c);
- c = gch();
- if( c != '*' ) goto swt;
- /* it really is a comment */
- Bputc(&fout, c);
- savline=yyline;
- while( c=gch() ){
- if( c=='*' ){
- Bputc(&fout, c);
- if( (c=gch()) == '/' ) goto loop;
- }
- Bputc(&fout, c);
- }
- yyline=savline;
- error( "EOF inside comment" );
- case '\'': /* character constant */
- mth = '\'';
- goto string;
- case '"': /* character string */
- mth = '"';
- string:
- Bputc(&fout, c);
- while( c=gch() ){
- if( c=='\\' ){
- Bputc(&fout, c);
- c=gch();
- }
- else if( c==mth ) goto loop;
- Bputc(&fout, c);
- if (c == '\n') {
- yyline--;
- error( "Non-terminated string or character constant");
- }
- }
- error( "EOF in string or character constant" );
- case '\0':
- yyline = savline;
- error("Action does not terminate");
- default:
- break; /* usual character */
- }
- loop:
- if(c != ' ' && c != '\t' && c != '\n') sw = FALSE;
- Bputc(&fout, c);
- }
- error("Premature EOF");
- return(0);
- }
- int
- gch(void){
- int c;
- prev = pres;
- c = pres = peek;
- peek = pushptr > pushc ? *--pushptr : Bgetc(fin);
- if(peek == Beof && sargc > 1){
- Bterm(fin);
- fin = Bopen(sargv[fptr++],OREAD);
- if(fin == 0)
- error("Cannot open file %s",sargv[fptr-1]);
- peek = Bgetc(fin);
- sargc--;
- sargv++;
- }
- if(c == Beof) {
- eof = TRUE;
- Bterm(fin);
- fin = 0;
- return(0);
- }
- if(c == '\n')yyline++;
- return(c);
- }
- int
- mn2(int a, int d, int c)
- {
- name[tptr] = a;
- left[tptr] = d;
- right[tptr] = c;
- parent[tptr] = 0;
- nullstr[tptr] = 0;
- switch(a){
- case RSTR:
- parent[d] = tptr;
- break;
- case BAR:
- case RNEWE:
- if(nullstr[d] || nullstr[c]) nullstr[tptr] = TRUE;
- parent[d] = parent[c] = tptr;
- break;
- case RCAT:
- case DIV:
- if(nullstr[d] && nullstr[c])nullstr[tptr] = TRUE;
- parent[d] = parent[c] = tptr;
- break;
- case RSCON:
- parent[d] = tptr;
- nullstr[tptr] = nullstr[d];
- break;
- # ifdef DEBUG
- default:
- warning("bad switch mn2 %d %d",a,d);
- break;
- # endif
- }
- if(tptr > treesize)
- error("Parse tree too big %s",(treesize == TREESIZE?"\nTry using %e num":""));
- return(tptr++);
- }
- int
- mnp(int a, void *p)
- {
- name[tptr] = a;
- left[tptr] = 0;
- parent[tptr] = 0;
- nullstr[tptr] = 0;
- ptr[tptr] = p;
- switch(a){
- case RCCL:
- case RNCCL:
- if(strlen(p) == 0) nullstr[tptr] = TRUE;
- break;
- default:
- error("bad switch mnp %d %P", a, p);
- break;
- }
- if(tptr > treesize)
- error("Parse tree too big %s",(treesize == TREESIZE?"\nTry using %e num":""));
- return(tptr++);
- }
- int
- mn1(int a, int d)
- {
- name[tptr] = a;
- left[tptr] = d;
- parent[tptr] = 0;
- nullstr[tptr] = 0;
- switch(a){
- case STAR:
- case QUEST:
- nullstr[tptr] = TRUE;
- parent[d] = tptr;
- break;
- case PLUS:
- case CARAT:
- nullstr[tptr] = nullstr[d];
- parent[d] = tptr;
- break;
- case S2FINAL:
- nullstr[tptr] = TRUE;
- break;
- # ifdef DEBUG
- case FINAL:
- case S1FINAL:
- break;
- default:
- warning("bad switch mn1 %d %d",a,d);
- break;
- # endif
- }
- if(tptr > treesize)
- error("Parse tree too big %s",(treesize == TREESIZE?"\nTry using %e num":""));
- return(tptr++);
- }
- int
- mn0(int a)
- {
- name[tptr] = a;
- parent[tptr] = 0;
- nullstr[tptr] = 0;
- if(a >= NCH) switch(a){
- case RNULLS: nullstr[tptr] = TRUE; break;
- # ifdef DEBUG
- default:
- warning("bad switch mn0 %d",a);
- break;
- # endif
- }
- if(tptr > treesize)
- error("Parse tree too big %s",(treesize == TREESIZE?"\nTry using %e num":""));
- return(tptr++);
- }
- void
- munputc(int p)
- {
- *pushptr++ = peek; /* watch out for this */
- peek = p;
- if(pushptr >= pushc+TOKENSIZE)
- error("Too many characters pushed");
- }
- void
- munputs(uchar *p)
- {
- int i,j;
- *pushptr++ = peek;
- peek = p[0];
- i = strlen((char*)p);
- for(j = i-1; j>=1; j--)
- *pushptr++ = p[j];
- if(pushptr >= pushc+TOKENSIZE)
- error("Too many characters pushed");
- }
- int
- dupl(int n)
- {
- /* duplicate the subtree whose root is n, return ptr to it */
- int i;
- i = name[n];
- if(i < NCH) return(mn0(i));
- switch(i){
- case RNULLS:
- return(mn0(i));
- case RCCL: case RNCCL:
- return(mnp(i,ptr[n]));
- case FINAL: case S1FINAL: case S2FINAL:
- return(mn1(i,left[n]));
- case STAR: case QUEST: case PLUS: case CARAT:
- return(mn1(i,dupl(left[n])));
- case RSTR: case RSCON:
- return(mn2(i,dupl(left[n]),right[n]));
- case BAR: case RNEWE: case RCAT: case DIV:
- return(mn2(i,dupl(left[n]),dupl(right[n])));
- # ifdef DEBUG
- default:
- warning("bad switch dupl %d",n);
- # endif
- }
- return(0);
- }
- # ifdef DEBUG
- void
- allprint(int c)
- {
- switch(c){
- case 014:
- print("\\f");
- charc++;
- break;
- case '\n':
- print("\\n");
- charc++;
- break;
- case '\t':
- print("\\t");
- charc++;
- break;
- case '\b':
- print("\\b");
- charc++;
- break;
- case ' ':
- print("\\\bb");
- break;
- default:
- if(!isprint(c)){
- print("\\%-3o",c);
- charc += 3;
- } else
- print("%c", c);
- break;
- }
- charc++;
- }
- void
- strpt(uchar *s)
- {
- charc = 0;
- while(*s){
- allprint(*s++);
- if(charc > LINESIZE){
- charc = 0;
- print("\n\t");
- }
- }
- }
- void
- sect1dump(void)
- {
- int i;
- print("Sect 1:\n");
- if(def[0]){
- print("str trans\n");
- i = -1;
- while(def[++i])
- print("%s\t%s\n",def[i],subs[i]);
- }
- if(sname[0]){
- print("start names\n");
- i = -1;
- while(sname[++i])
- print("%s\n",sname[i]);
- }
- }
- void
- sect2dump(void)
- {
- print("Sect 2:\n");
- treedump();
- }
- void
- treedump(void)
- {
- int t;
- uchar *p;
- print("treedump %d nodes:\n",tptr);
- for(t=0;t<tptr;t++){
- print("%4d ",t);
- parent[t] ? print("p=%4d",parent[t]) : print(" ");
- print(" ");
- if(name[t] < NCH)
- allprint(name[t]);
- else switch(name[t]){
- case RSTR:
- print("%d ",left[t]);
- allprint(right[t]);
- break;
- case RCCL:
- print("ccl ");
- allprint(ptr[t]);
- break;
- case RNCCL:
- print("nccl ");
- allprint(ptr[t]);
- break;
- case DIV:
- print("/ %d %d",left[t],right[t]);
- break;
- case BAR:
- print("| %d %d",left[t],right[t]);
- break;
- case RCAT:
- print("cat %d %d",left[t],right[t]);
- break;
- case PLUS:
- print("+ %d",left[t]);
- break;
- case STAR:
- print("* %d",left[t]);
- break;
- case CARAT:
- print("^ %d",left[t]);
- break;
- case QUEST:
- print("? %d",left[t]);
- break;
- case RNULLS:
- print("nullstring");
- break;
- case FINAL:
- print("final %d",left[t]);
- break;
- case S1FINAL:
- print("s1final %d",left[t]);
- break;
- case S2FINAL:
- print("s2final %d",left[t]);
- break;
- case RNEWE:
- print("new %d %d",left[t],right[t]);
- break;
- case RSCON:
- p = (uchar *)right[t];
- print("start %s",sname[*p++-1]);
- while(*p)
- print(", %s",sname[*p++-1]);
- print(" %d",left[t]);
- break;
- default:
- print("unknown %d %d %d",name[t],left[t],right[t]);
- break;
- }
- if(nullstr[t])print("\t(null poss.)");
- print("\n");
- }
- }
- # endif
|