henesyinit from p9fce6d0435 years agoHistory
290 lines · 7.3 KB · Text
RawDownload
%Start A str sc reg comment %{/*Copyright (c) 1989 AT&T	All Rights Reserved THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF AT&T. The copyright notice above does not evidence anyactual or intended publication of such source code.*/ #undef	input	/* defeat lex */#undef	unput #include <stdlib.h>#include <string.h>#include "awk.h"#include "y.tab.h" extern YYSTYPE	yylval;extern int	infunc; int	lineno	= 1;int	bracecnt = 0;int	brackcnt  = 0;int	parencnt = 0;int	runecnt = 0; #ifdef	DEBUG#	define	RET(x)	{if(dbg)printf("lex %s [%s]\n", tokname(x), yytext); return(x); }#else#	define	RET(x)	return(x)#endif #define	CADD	cbuf[clen++] = yytext[0]; \		if (clen >= CBUFLEN-1) { \			ERROR "string/reg expr %.30s... too long", cbuf SYNTAX; \			BEGIN A; \		} uchar	cbuf[CBUFLEN];uchar	*s;int	clen, cflag;%} A	[a-zA-Z_]B	[a-zA-Z0-9_]D	[0-9]O	[0-7]H	[0-9a-fA-F]WS	[ \t] %%	switch (yybgin-yysvec-1) {	/* witchcraft */	case 0:		BEGIN A;		break;	case sc:		BEGIN A;		RET('}');	} <A>\n		{ lineno++; RET(NL); }<A>#.*		{ ; }	/* strip comments */<A>{WS}+	{ ; }<A>;		{ RET(';'); } <A>"\\"\n	{ lineno++; }<A>BEGIN	{ RET(XBEGIN); }<A>END		{ RET(XEND); }<A>func(tion)?	{ if (infunc) ERROR "illegal nested function" SYNTAX; RET(FUNC); }<A>return	{ if (!infunc) ERROR "return not in function" SYNTAX; RET(RETURN); }<A>"&&"		{ RET(AND); }<A>"||"		{ RET(BOR); }<A>"!"		{ RET(NOT); }<A>"!="		{ yylval.i = NE; RET(NE); }<A>"~"		{ yylval.i = MATCH; RET(MATCHOP); }<A>"!~"		{ yylval.i = NOTMATCH; RET(MATCHOP); }<A>"<"		{ yylval.i = LT; RET(LT); }<A>"<="		{ yylval.i = LE; RET(LE); }<A>"=="		{ yylval.i = EQ; RET(EQ); }<A>">="		{ yylval.i = GE; RET(GE); }<A>">"		{ yylval.i = GT; RET(GT); }<A>">>"		{ yylval.i = APPEND; RET(APPEND); }<A>"++"		{ yylval.i = INCR; RET(INCR); }<A>"--"		{ yylval.i = DECR; RET(DECR); }<A>"+="		{ yylval.i = ADDEQ; RET(ASGNOP); }<A>"-="		{ yylval.i = SUBEQ; RET(ASGNOP); }<A>"*="		{ yylval.i = MULTEQ; RET(ASGNOP); }<A>"/="		{ yylval.i = DIVEQ; RET(ASGNOP); }<A>"%="		{ yylval.i = MODEQ; RET(ASGNOP); }<A>"^="		{ yylval.i = POWEQ; RET(ASGNOP); }<A>"**="	{ yylval.i = POWEQ; RET(ASGNOP); }<A>"="		{ yylval.i = ASSIGN; RET(ASGNOP); }<A>"**"		{ RET(POWER); }<A>"^"		{ RET(POWER); } <A>"$"{D}+	{ yylval.cp = fieldadr(atoi(yytext+1)); RET(FIELD); }<A>"$NF"	{ unputstr("(NF)"); return(INDIRECT); }<A>"$"{A}{B}*	{ int c, n;		  c = input(); unput(c);		  if (c == '(' || c == '[' || infunc && (n=isarg(yytext+1)) >= 0) {			unputstr(yytext+1);			return(INDIRECT);		  } else {			yylval.cp = setsymtab(yytext+1,"",0.0,STR|NUM,symtab);			RET(IVAR);		  }		}<A>"$"		{ RET(INDIRECT); }<A>NF		{ yylval.cp = setsymtab(yytext, "", 0.0, NUM, symtab); RET(VARNF); } <A>({D}+("."?){D}*|"."{D}+)((e|E)("+"|-)?{D}+)?	{		  yylval.cp = setsymtab(yytext, tostring(yytext), atof(yytext), CON|NUM, symtab);		/* should this also have STR set? */		  RET(NUMBER); } <A>while	{ RET(WHILE); }<A>for		{ RET(FOR); }<A>do		{ RET(DO); }<A>if		{ RET(IF); }<A>else		{ RET(ELSE); }<A>next		{ RET(NEXT); }<A>exit		{ RET(EXIT); }<A>break	{ RET(BREAK); }<A>continue	{ RET(CONTINUE); }<A>print	{ yylval.i = PRINT; RET(PRINT); }<A>printf	{ yylval.i = PRINTF; RET(PRINTF); }<A>sprintf	{ yylval.i = SPRINTF; RET(SPRINTF); }<A>split	{ yylval.i = SPLIT; RET(SPLIT); }<A>substr	{ RET(SUBSTR); }<A>sub		{ yylval.i = SUB; RET(SUB); }<A>gsub		{ yylval.i = GSUB; RET(GSUB); }<A>index	{ RET(INDEX); }<A>match	{ RET(MATCHFCN); }<A>in		{ RET(IN); }<A>getline	{ RET(GETLINE); }<A>close	{ RET(CLOSE); }<A>delete	{ RET(DELETE); }<A>length	{ yylval.i = FLENGTH; RET(BLTIN); }<A>log		{ yylval.i = FLOG; RET(BLTIN); }<A>int		{ yylval.i = FINT; RET(BLTIN); }<A>exp		{ yylval.i = FEXP; RET(BLTIN); }<A>sqrt		{ yylval.i = FSQRT; RET(BLTIN); }<A>sin		{ yylval.i = FSIN; RET(BLTIN); }<A>cos		{ yylval.i = FCOS; RET(BLTIN); }<A>atan2	{ yylval.i = FATAN; RET(BLTIN); }<A>system	{ yylval.i = FSYSTEM; RET(BLTIN); }<A>rand		{ yylval.i = FRAND; RET(BLTIN); }<A>srand	{ yylval.i = FSRAND; RET(BLTIN); }<A>toupper	{ yylval.i = FTOUPPER; RET(BLTIN); }<A>tolower	{ yylval.i = FTOLOWER; RET(BLTIN); }<A>fflush	{ yylval.i = FFLUSH; RET(BLTIN); }<A>utf	{ yylval.i = FUTF; RET(BLTIN); } <A>{A}{B}*	{ int n, c;		  c = input(); unput(c);	/* look for '(' */		  if (c != '(' && infunc && (n=isarg(yytext)) >= 0) {			yylval.i = n;			RET(ARG);		  } else {			yylval.cp = setsymtab(yytext,"",0.0,STR|NUM,symtab);			if (c == '(') {				RET(CALL);			} else {				RET(VAR);			}		  }		}<A>\"		{ BEGIN str; clen = 0; } <A>"}"		{ if (--bracecnt < 0) ERROR "extra }" SYNTAX; BEGIN sc; RET(';'); }<A>"]"		{ if (--brackcnt < 0) ERROR "extra ]" SYNTAX; RET(']'); }<A>")"		{ if (--parencnt < 0) ERROR "extra )" SYNTAX; RET(')'); } <A>.		{ if (yytext[0] == '{') bracecnt++;		  else if (yytext[0] == '[') brackcnt++;		  else if (yytext[0] == '(') parencnt++;		  RET(yylval.i = yytext[0]); /* everything else */ } <reg>\\.	{ cbuf[clen++] = '\\'; cbuf[clen++] = yytext[1]; }<reg>\n		{ ERROR "newline in regular expression %.10s...", cbuf SYNTAX; lineno++; BEGIN A; }<reg>"/"	{ BEGIN A;		  cbuf[clen] = 0;		  yylval.s = tostring(cbuf);		  unput('/');		  RET(REGEXPR); }<reg>.		{ int uc, i;		  CADD;		  uc = *((uchar *)yytext)&0xFF;		  if (uc & 0x80) {			i = 0x40;			while (uc&i) {				cbuf[clen++] = input();				i >>= 1;		  	}		  }		} <str>\"		{ BEGIN A;		  cbuf[clen] = 0; s = tostring(cbuf);		  cbuf[clen] = ' '; cbuf[++clen] = 0;		  yylval.cp = setsymtab(cbuf, s, 0.0, CON|STR, symtab);		  RET(STRING); }<str>\n		{ ERROR "newline in string %.10s...", cbuf SYNTAX; lineno++; BEGIN A; }<str>"\\\""	{ cbuf[clen++] = '"'; }<str>"\\"n	{ cbuf[clen++] = '\n'; }<str>"\\"t	{ cbuf[clen++] = '\t'; }<str>"\\"f	{ cbuf[clen++] = '\f'; }<str>"\\"r	{ cbuf[clen++] = '\r'; }<str>"\\"b	{ cbuf[clen++] = '\b'; }<str>"\\"v	{ cbuf[clen++] = '\v'; }	/* these ANSIisms may not be known by */<str>"\\"a	{ cbuf[clen++] = '\007'; }	/* your compiler. hence 007 for bell */<str>"\\\\"	{ cbuf[clen++] = '\\'; }<str>"\\"({O}{O}{O}|{O}{O}|{O}) { int n;		  sscanf(yytext+1, "%o", &n); cbuf[clen++] = n; }<str>"\\"x({H}+) { int n;	/* ANSI permits any number! */		  sscanf(yytext+2, "%x", &n); cbuf[clen++] = n; }<str>"\\".	{ cbuf[clen++] = yytext[1]; }<str>.		{ int uc, i;		  CADD;		  uc = *((uchar *)yytext)&0xFF;		  if (uc & 0x80) {			i = 0x40;			while (uc&i) {				cbuf[clen++] = input();				i >>= 1;		  	}		  }		} %% void startreg(void)	/* start parsing a regular expression */{	BEGIN reg;	clen = 0;} /* input() and unput() are transcriptions of the standard lex   macros for input and output with additions for error message   printing.  God help us all if someone changes how lex works.*/ uchar	ebuf[300];uchar	*ep = ebuf; input(void)	/* get next lexical input character */{	register int c;	extern uchar *lexprog; 	if (yysptr > yysbuf)		c = U(*--yysptr)&0xff;	else if (lexprog != NULL) {	/* awk '...' */		if (c = (*lexprog&0xff))			lexprog++;	} else				/* awk -f ... */		c = pgetc();	if (c == '\n')		yylineno++;	else if (c == EOF)		c = 0;	if (ep >= ebuf + sizeof ebuf)		ep = ebuf;	c &= 0xFF;	*ep++ = c;	return c;} void unput(int c)	/* put lexical character back on input */{	yytchar = c;	if (yytchar == '\n')		yylineno--;	*yysptr++ = yytchar;	if (--ep < ebuf)		ep = ebuf + sizeof(ebuf) - 1;}  void unputstr(char *s)	/* put a string back on input */{	int i; 	for (i = strlen(s)-1; i >= 0; i--)		unput(s[i]);}