home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
GEMini Atari
/
GEMini_Atari_CD-ROM_Walnut_Creek_December_1993.iso
/
files
/
language
/
sozobon2
/
lex.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-10-23
|
8KB
|
302 lines
/*
* Copyright (c) 1988 by Sozobon, Limited. Author: Joseph M Treat
*
* Permission is granted to anyone to use this software for any purpose
* on any computer system, and to redistribute it freely, with the
* following restrictions:
* 1) No charge may be made other than reasonable charges for reproduction.
* 2) Modified versions must be clearly marked as such.
* 3) The authors are not responsible for any harmful consequences
* of using this software, even if they result from defects in it.
*/
#include "jas.h"
#include "scan.h"
#include "parse.h"
extern do_star;
struct reserved words[] = {
/*
* alphabetized list of reserved words
*/
{ ".bss", _BSS, 0 },
{ ".comm", _COMM, 0 },
{ ".data", _DATA, 0 },
{ ".dc", _DC, 0 },
{ ".ds", _DS, 0 },
{ ".end", END, 0 },
{ ".equ", _EQU, 0 },
{ ".even", _EVEN, 0 },
{ ".globl", _GLOBL, 0 },
{ ".org", _ORG, 0 },
{ ".text", _TEXT, 0 },
{ "a0", REG, 8 },
{ "a1", REG, 9 },
{ "a2", REG, 10 },
{ "a3", REG, 11 },
{ "a4", REG, 12 },
{ "a5", REG, 13 },
{ "a6", REG, 14 },
{ "a7", REG, 15 },
{ "bss", _BSS, 0 },
{ "ccr", SREG, O_CCR },
{ "comm", _COMM, 0 },
{ "d0", REG, 0 },
{ "d1", REG, 1 },
{ "d2", REG, 2 },
{ "d3", REG, 3 },
{ "d4", REG, 4 },
{ "d5", REG, 5 },
{ "d6", REG, 6 },
{ "d7", REG, 7 },
{ "data", _DATA, 0 },
{ "dc", _DC, 0 },
{ "ds", _DS, 0 },
{ "end", END, 0 },
{ "equ", _EQU, 0 },
{ "even", _EVEN, 0 },
{ "globl", _GLOBL, 0 },
{ "org", _ORG, 0 },
{ "pc", PC, 0 },
{ "sp", REG, 15 },
{ "sr", SREG, O_SR },
{ "text", _TEXT, 0 },
{ "usp", SREG, O_USP },
{ "", 0, 0 }
};
int nwords = (sizeof words) / (sizeof (struct reserved));
struct lexacts actions[256];
struct lextab lextab[] = {
{ '\t', { L_SKIP, 0 } },
{ '\n', { L_TOKEN, NL } },
{ '\r', { L_SKIP, 0 } },
{ ' ', { L_SKIP, 0 } },
{ '"', { L_EXTRA|L_TOKEN, ERR } },
{ '\'', { L_EXTRA|L_TOKEN, ERR } },
{ '%', { L_TOKEN, MOD } },
{ '(', { L_TOKEN, LP } },
{ ')', { L_TOKEN, RP } },
{ '*', { L_TOKEN, STAR } },
{ '-', { L_TOKEN, MINUS } },
{ '+', { L_TOKEN, PLUS } },
{ ',', { L_TOKEN, COMMA } },
{ '/', { L_EXTRA|L_TOKEN, DIV } },
{ '~', { L_EXTRA|L_TOKEN, NOT } },
{ '#', { L_TOKEN, POUND } },
{ '@', { L_EXTRA|L_DIGIT, NUMBER } },
{ '$', { L_EXTRA|L_DIGIT, NUMBER } },
{ '0', { L_MIDID|L_DIGIT, NUMBER } },
{ '1', { L_MIDID|L_DIGIT, NUMBER } },
{ '2', { L_MIDID|L_DIGIT, NUMBER } },
{ '3', { L_MIDID|L_DIGIT, NUMBER } },
{ '4', { L_MIDID|L_DIGIT, NUMBER } },
{ '5', { L_MIDID|L_DIGIT, NUMBER } },
{ '6', { L_MIDID|L_DIGIT, NUMBER } },
{ '7', { L_MIDID|L_DIGIT, NUMBER } },
{ '8', { L_MIDID|L_DIGIT, NUMBER } },
{ '9', { L_MIDID|L_DIGIT, NUMBER } },
{ ':', { L_TOKEN, COLON } },
{ ';', { L_TOKEN|L_EXTRA, COMMENT } },
{ '<', { L_EXTRA|L_TOKEN, ERR } },
{ '>', { L_EXTRA|L_TOKEN, ERR } },
{ 'A', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'B', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'C', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'D', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'E', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'F', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'G', { L_BEGID|L_MIDID, NAME } },
{ 'H', { L_BEGID|L_MIDID, NAME } },
{ 'I', { L_BEGID|L_MIDID, NAME } },
{ 'J', { L_BEGID|L_MIDID, NAME } },
{ 'K', { L_BEGID|L_MIDID, NAME } },
{ 'L', { L_BEGID|L_MIDID, NAME } },
{ 'M', { L_BEGID|L_MIDID, NAME } },
{ 'N', { L_BEGID|L_MIDID, NAME } },
{ 'O', { L_BEGID|L_MIDID, NAME } },
{ 'P', { L_BEGID|L_MIDID, NAME } },
{ 'Q', { L_BEGID|L_MIDID, NAME } },
{ 'R', { L_BEGID|L_MIDID, NAME } },
{ 'S', { L_BEGID|L_MIDID, NAME } },
{ 'T', { L_BEGID|L_MIDID, NAME } },
{ 'U', { L_BEGID|L_MIDID, NAME } },
{ 'V', { L_BEGID|L_MIDID, NAME } },
{ 'W', { L_BEGID|L_MIDID, NAME } },
{ 'X', { L_BEGID|L_MIDID, NAME } },
{ 'Y', { L_BEGID|L_MIDID, NAME } },
{ 'Z', { L_BEGID|L_MIDID, NAME } },
{ '.', { L_BEGID|L_MIDID, NAME } },
{ '_', { L_BEGID|L_MIDID, NAME } },
{ 'a', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'b', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'c', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'd', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'e', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'f', { L_BEGID|L_MIDID|L_DIGIT, NAME } },
{ 'g', { L_BEGID|L_MIDID, NAME } },
{ 'h', { L_BEGID|L_MIDID, NAME } },
{ 'i', { L_BEGID|L_MIDID, NAME } },
{ 'j', { L_BEGID|L_MIDID, NAME } },
{ 'k', { L_BEGID|L_MIDID, NAME } },
{ 'l', { L_BEGID|L_MIDID, NAME } },
{ 'm', { L_BEGID|L_MIDID, NAME } },
{ 'n', { L_BEGID|L_MIDID, NAME } },
{ 'o', { L_BEGID|L_MIDID, NAME } },
{ 'p', { L_BEGID|L_MIDID, NAME } },
{ 'q', { L_BEGID|L_MIDID, NAME } },
{ 'r', { L_BEGID|L_MIDID, NAME } },
{ 's', { L_BEGID|L_MIDID, NAME } },
{ 't', { L_BEGID|L_MIDID, NAME } },
{ 'u', { L_BEGID|L_MIDID, NAME } },
{ 'v', { L_BEGID|L_MIDID, NAME } },
{ 'w', { L_BEGID|L_MIDID, NAME } },
{ 'x', { L_BEGID|L_MIDID, NAME } },
{ 'y', { L_BEGID|L_MIDID, NAME } },
{ 'z', { L_BEGID|L_MIDID, NAME } }
};
struct lexacts deflexact = { L_TOKEN, ERR };
static int lextabsize = (sizeof lextab) / (sizeof (struct lextab));
yyinit()
{
{
register struct lexacts *ap;
for ( ap = actions; ap < &actions[256]; ap++ )
*ap = deflexact;
}
{
register struct lextab *lp;
register struct lextab *ep;
ep = &lextab[lextabsize];
for ( lp = lextab; lp < ep; lp++ )
actions[lp->select] = lp->action;
}
}
yyprocess( c )
register char c;
{
register int i;
char buf[256];
extern YYSTYPE yylval;
extern int line;
switch ( c ) {
case '/':
c = yygetc();
if ( c != '*' ) {
yyungetc( c );
return 0;
}
do_star = 0;
for ( c = yygetc(); c; c = yygetc()) {
if ( c == '\n' ) {
line++;
} else {
if ( c == '*' ) {
c = yygetc();
if ( c == '/' ) {
do_star = 1;
return COMMENT;
}
yyungetc( c );
}
}
}
error( line, "non-terminated comment");
case '\'':
do_star = 0;
c = yygetc();
for ( i = 0; c; ) {
buf[i++] = c;
if ( c == '\\' )
buf[i++] = yygetc();
c = yygetc();
if ( c == '\'' )
break;
}
if (! c )
error( line, "non-terminated string" );
buf[i] = '\0';
yylval.str = STRCPY( buf );
do_star = 1;
return STRING;
case '"':
do_star = 0;
c = yygetc();
for (i = 0; c; ) {
buf[i++] = c;
if ( c == '\\' )
buf[i++] = yygetc();
c = yygetc();
if ( c == '"' )
break;
}
if (! c )
error( line, "non-terminated string" );
buf[i] = '\0';
yylval.str = STRCPY( buf );
do_star = 1;
return STRING;
case '<':
c = yygetc();
if ( c == '<' )
return LSH;
yyungetc( c );
return 0;
case '>':
c = yygetc();
if ( c == '>' )
return RSH;
yyungetc( c );
return 0;
case '@':
c = yygetc();
if ( c >= '0' && c <= '7' ) {
yyungetc( c );
return 0;
}
return ERR;
case '$':
c = yygetc();
if ( c >= '0' && c <= '9' ||
c >= 'a' && c <= 'f' ||
c >= 'A' && c <= 'F' ) {
yyungetc( c );
return 0;
}
return ERR;
case ';':
do_star = 0;
do {
c = yygetc();
} while ( c && c != '\n' );
if ( c )
yyungetc( c );
do_star = 1;
return COMMENT;
default:
return 0;
}
}
yymodify( buf )
char *buf;
{
register char *cp;
for ( cp = buf; *cp; cp++ )
if ( isupper( *cp ) )
*cp = toupper( *cp );
}