📄 scan.c
字号:
# include "mfile1"# include <ctype.h> /* temporarily */ /* lexical actions */# define A_ERR 0 /* illegal character */# define A_LET 1 /* saw a letter */# define A_DIG 2 /* saw a digit */# define A_1C 3 /* return a single character */# define A_STR 4 /* string */# define A_CC 5 /* character constant */# define A_BCD 6 /* GCOS BCD constant */# define A_SL 7 /* saw a / */# define A_DOT 8 /* saw a . */# define A_PL 9 /* + */# define A_MI 10 /* - */# define A_EQ 11 /* = */# define A_NOT 12 /* ! */# define A_LT 13 /* < */# define A_GT 14 /* > */# define A_AND 16 /* & */# define A_OR 17 /* | */# define A_WS 18 /* whitespace (not \n) */# define A_NL 19 /* \n */ /* character classes */# define LEXLET 01# define LEXDIG 02# define LEXOCT 04# define LEXHEX 010# define LEXWS 020# define LEXDOT 040 /* reserved word actions */# define AR_TY 0 /* type word */# define AR_RW 1 /* simple reserved word */# define AR_CL 2 /* storage class word */# define AR_S 3 /* struct */# define AR_U 4 /* union */# define AR_E 5 /* enum */# define AR_A 6 /* asm */ /* text buffer */# define LXTSZ 100char yytext[LXTSZ];char * lxgcp; /* ARGSUSED */mainp1( argc, argv ) int argc; char *argv[]; { /* control multiple files */ register i; register char *cp; extern int idebug, bdebug, tdebug, edebug, ddebug, xdebug; for( i=1; i<argc; ++i ){ if( *(cp=argv[i]) == '-' && *++cp == 'X' ){ while( *++cp ){ switch( *cp ){ case 'd': ++ddebug; break; case 'i': ++idebug; break; case 'b': ++bdebug; break; case 't': ++tdebug; break; case 'e': ++edebug; break; case 'x': ++xdebug; break; } } } }# ifdef ONEPASS p2init( argc, argv );# endif for( i=0; i<SYMTSZ; ++i ) stab[i].stype = TNULL; lxinit(); tinit(); mkdope(); lineno = 1; /* dimension table initialization */ dimtab[NULL] = 0; dimtab[CHAR] = SZCHAR; dimtab[INT] = SZINT; dimtab[FLOAT] = SZFLOAT; dimtab[DOUBLE] = SZDOUBLE; dimtab[LONG] = SZLONG; dimtab[SHORT] = SZSHORT; dimtab[UCHAR] = SZCHAR; dimtab[USHORT] = SZSHORT; dimtab[UNSIGNED] = SZINT; dimtab[ULONG] = SZLONG; /* starts past any of the above */ curdim = 16; reached = 1; yyparse(); yyaccpt(); ejobcode( nerrors ? 1 : 0 ); return(nerrors?1:0); }# ifdef ibm# define CSMASK 0377# define CSSZ 256# else# define CSMASK 0177# define CSSZ 128# endifshort lxmask[CSSZ+1];lxenter( s, m ) register char *s; register short m; { /* enter a mask into lxmask */ register c; while( c= *s++ ) lxmask[c+1] |= m; }# define lxget(c,m) (lxgcp=yytext,lxmore(c,m))lxmore( c, m ) register c, m; { register char *cp; *(cp = lxgcp) = c; while( c=getchar(), lxmask[c+1]&m ){ if( cp < &yytext[LXTSZ-1] ){ *++cp = c; } } ungetc(c,stdin); *(lxgcp = cp+1) = '\0'; }struct lxdope { short lxch; /* the character */ short lxact; /* the action to be performed */ short lxtok; /* the token number to be returned */ short lxval; /* the value to be returned */ } lxdope[] = { '$', A_ERR, 0, 0, /* illegal characters go here... */ '_', A_LET, 0, 0, /* letters point here */ '0', A_DIG, 0, 0, /* digits point here */ ' ', A_WS, 0, 0, /* whitespace goes here */ '\n', A_NL, 0, 0, '"', A_STR, 0, 0, /* character string */ '\'', A_CC, 0, 0, /* character constant */ '`', A_BCD, 0, 0, /* GCOS BCD constant */ '(', A_1C, LP, 0, ')', A_1C, RP, 0, '{', A_1C, LC, 0, '}', A_1C, RC, 0, '[', A_1C, LB, 0, ']', A_1C, RB, 0, '*', A_1C, MUL, MUL, '?', A_1C, QUEST, 0, ':', A_1C, COLON, 0, '+', A_PL, PLUS, PLUS, '-', A_MI, MINUS, MINUS, '/', A_SL, DIVOP, DIV, '%', A_1C, DIVOP, MOD, '&', A_AND, AND, AND, '|', A_OR, OR, OR, '^', A_1C, ER, ER, '!', A_NOT, UNOP, NOT, '~', A_1C, UNOP, COMPL, ',', A_1C, CM, CM, ';', A_1C, SM, 0, '.', A_DOT, STROP, DOT, '<', A_LT, RELOP, LT, '>', A_GT, RELOP, GT, '=', A_EQ, ASSIGN, ASSIGN, -1, A_1C, 0, 0, };struct lxdope *lxcp[CSSZ+1];lxinit(){ register struct lxdope *p; register i; register char *cp; /* set up character classes */ lxenter( "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_", LEXLET ); lxenter( "0123456789", LEXDIG ); lxenter( "0123456789abcdefABCDEF", LEXHEX ); lxenter( " \t\r\b\f", LEXWS ); lxenter( "01234567", LEXOCT ); lxmask['.'+1] |= LEXDOT; /* make lxcp point to appropriate lxdope entry for each character */ /* initialize error entries */ for( i= 0; i<=CSSZ; ++i ) lxcp[i] = lxdope; /* make unique entries */ for( p=lxdope; ; ++p ) { lxcp[p->lxch+1] = p; if( p->lxch < 0 ) break; } /* handle letters, digits, and whitespace */ /* by convention, first, second, and third places */ cp = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; while( *cp ) lxcp[*cp++ + 1] = &lxdope[1]; cp = "123456789"; while( *cp ) lxcp[*cp++ + 1] = &lxdope[2]; cp = "\t\b\r\f"; while( *cp ) lxcp[*cp++ + 1] = &lxdope[3]; /* first line might have title */ lxtitle(); }int lxmatch; /* character to be matched in char or string constant */lxstr(ct){ /* match a string or character constant, up to lxmatch */ register c; register val; register i; i=0; while( (c=getchar()) != lxmatch ){ switch( c ) { case EOF: uerror( "unexpected EOF" ); break; case '\n': uerror( "newline in string or char constant" ); ++lineno; break; case '\\': switch( c = getchar() ){ case '\n': ++lineno; continue; default: val = c; goto mkcc; case 'n': val = '\n'; goto mkcc; case 'r': val = '\r'; goto mkcc; case 'b': val = '\b'; goto mkcc; case 't': val = '\t'; goto mkcc; case 'f': val = '\f'; goto mkcc; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': val = c-'0'; c=getchar(); /* try for 2 */ if( lxmask[c+1] & LEXOCT ){ val = (val<<3) | (c-'0'); c = getchar(); /* try for 3 */ if( lxmask[c+1] & LEXOCT ){ val = (val<<3) | (c-'0'); } else ungetc( c ,stdin); } else ungetc( c ,stdin); goto mkcc1; } default: val =c; mkcc: val = CCTRANS(val); mkcc1: if( lxmatch == '\'' ){ val = CHARCAST(val); /* it is, after all, a "character" constant */ makecc( val, i ); } else { /* stash the byte into the string */ if( strflg ) { if( ct==0 || i<ct ) putbyte( val ); else if( i == ct ) werror( "non-null byte ignored in string initializer" ); } else bycode( val, i ); } ++i; continue; } break; } /* end of string or char constant */ if( lxmatch == '"' ){ if( strflg ){ /* end the string */ if( ct==0 || i<ct ) putbyte( 0 ); /* the null at the end */ } else { /* the initializer gets a null byte */ bycode( 0, i++ ); bycode( -1, i ); dimtab[curdim] = i; /* in case of later sizeof ... */ } } else { /* end the character constant */ if( i == 0 ) uerror( "empty character constant" ); if( i>(SZINT/SZCHAR) || ( (pflag||hflag)&&i>1) ) uerror( "too many characters in character constant" ); } }lxcom(){ register c; /* saw a /*: process a comment */ for(;;){ switch( c = getchar() ){ case EOF: uerror( "unexpected EOF" ); return; case '\n': ++lineno; default: continue; case '*': if( (c = getchar()) == '/' ) return; else ungetc( c ,stdin); continue;# ifdef LINT case 'V': lxget( c, LEXLET|LEXDIG ); { extern int vaflag; int i; i = yytext[7]?yytext[7]-'0':0; yytext[7] = '\0'; if( strcmp( yytext, "VARARGS" ) ) continue; vaflag = i; continue; } case 'L': lxget( c, LEXLET ); if( strcmp( yytext, "LINTLIBRARY" ) ) continue; { extern int libflag; libflag = 1; } continue; case 'A': lxget( c, LEXLET ); if( strcmp( yytext, "ARGSUSED" ) ) continue; { extern int argflag, vflag; argflag = 1; vflag = 0; } continue; case 'N': lxget( c, LEXLET ); if( strcmp( yytext, "NOTREACHED" ) ) continue; reached = 0; continue;# endif } } }yylex(){ for(;;){ register lxchar; register struct lxdope *p; register struct symtab *sp; int id; switch( (p=lxcp[(lxchar=getchar())+1])->lxact ){ onechar: ungetc( lxchar ,stdin); case A_1C: /* eat up a single character, and return an opcode */ yylval.intval = p->lxval; return( p->lxtok ); case A_ERR: uerror( "illegal character: %03o (octal)", lxchar ); break; case A_LET: /* collect an identifier, check for reserved word, and return */ lxget( lxchar, LEXLET|LEXDIG ); if( (lxchar=lxres()) > 0 ) return( lxchar ); /* reserved word */ if( lxchar== 0 ) continue; id = lookup( yytext, (stwart&(INSTRUCT|INUNION|FUNNYNAME))?SMOS:0 ); sp = &stab[id]; if( sp->sclass == TYPEDEF && !stwart ){ stwart = instruct; yylval.nodep = mkty( sp->stype, sp->dimoff, sp->sizoff ); return( TYPE ); } stwart = (stwart&SEENAME) ? instruct : 0; yylval.intval = id; return( NAME ); case A_DIG: /* collect a digit string, then look at last one... */ lastcon = 0; lxget( lxchar, LEXDIG );
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -