From e37302c4b99f147f1fd85ca27a2dbd2aa7a4eb41 Mon Sep 17 00:00:00 2001 From: wkj Date: Wed, 21 Apr 2004 01:22:09 +0000 Subject: Plan 9 lex (to be installed as lex.9, if at all). --- src/cmd/lex/sub1.c | 591 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 591 insertions(+) create mode 100644 src/cmd/lex/sub1.c (limited to 'src/cmd/lex/sub1.c') diff --git a/src/cmd/lex/sub1.c b/src/cmd/lex/sub1.c new file mode 100644 index 00000000..cb393a46 --- /dev/null +++ b/src/cmd/lex/sub1.c @@ -0,0 +1,591 @@ +# 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) return; + i = cindex[i]; + /* see if ccl is already in our table */ + j = 0; + if(i){ + for(j=1;j= NCH) return; /* already in */ + m = 0; + k = 0; + for(i=1;i 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); + 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 +mn1(int a, int d) +{ + name[tptr] = a; + left[tptr] = d; + parent[tptr] = 0; + nullstr[tptr] = 0; + switch(a){ + case RCCL: + case RNCCL: + if(strlen((char *)d) == 0) nullstr[tptr] = TRUE; + break; + 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: 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