#include <stdio.h>
#include <string.h>
+// Make the scope character ('.') be a symbol, otherwise it's just
+// a ident character
#define USE_SCOPE_CHAR 0
#define DEBUG 0
const char *Name;
} csaReservedWords[] = {
{TOK_RWD_FUNCTION, "function"},
+
{TOK_RWD_RETURN, "return"},
+ {TOK_RWD_NEW, "new"},
+
+ {TOK_RWD_IF, "if"},
+ {TOK_RWD_ELSE, "else"},
+ {TOK_RWD_DO, "do"},
+ {TOK_RWD_WHILE, "while"},
+ {TOK_RWD_FOR, "for"},
+
{TOK_RWD_VOID, "void"},
{TOK_RWD_OBJECT, "Object"},
+ {TOK_RWD_OPAQUE, "Opaque"},
{TOK_RWD_INTEGER, "Integer"},
{TOK_RWD_REAL, "Real"},
{TOK_RWD_STRING, "String"}
case '\0': ret = TOK_EOF; break;
// Operations
- case '/': ret = TOK_DIV; break;
- case '*': ret = TOK_MUL; break;
- case '+': ret = TOK_PLUS; break;
+ case '^':
+ if( *File->CurPos == '^' ) {
+ File->CurPos ++;
+ ret = TOK_LOGICXOR;
+ break;
+ }
+ ret = TOK_XOR;
+ break;
+
+ case '|':
+ if( *File->CurPos == '|' ) {
+ File->CurPos ++;
+ ret = TOK_LOGICOR;
+ break;
+ }
+ ret = TOK_OR;
+ break;
+
+ case '&':
+ if( *File->CurPos == '&' ) {
+ File->CurPos ++;
+ ret = TOK_LOGICAND;
+ break;
+ }
+ ret = TOK_AND;
+ break;
+
+ case '/':
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_ASSIGN_DIV;
+ break;
+ }
+ ret = TOK_DIV;
+ break;
+ case '*':
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_ASSIGN_MUL;
+ break;
+ }
+ ret = TOK_MUL;
+ break;
+ case '+':
+ if( *File->CurPos == '+' ) {
+ File->CurPos ++;
+ ret = TOK_INCREMENT;
+ break;
+ }
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_ASSIGN_PLUS;
+ break;
+ }
+ ret = TOK_PLUS;
+ break;
case '-':
+ if( *File->CurPos == '-' ) {
+ File->CurPos ++;
+ ret = TOK_DECREMENT;
+ break;
+ }
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_ASSIGN_MINUS;
+ break;
+ }
if( *File->CurPos == '>' ) {
File->CurPos ++;
ret = TOK_ELEMENT;
+ break;
}
- else
- ret = TOK_MINUS;
+ ret = TOK_MINUS;
break;
// Strings
case '"':
while( *File->CurPos && !(*File->CurPos == '"' && *File->CurPos != '\\') )
File->CurPos ++;
- File->CurPos ++;
- ret = TOK_STR;
+ if( *File->CurPos )
+ {
+ File->CurPos ++;
+ ret = TOK_STR;
+ }
+ else
+ ret = TOK_EOF;
break;
// Brackets
ret = TOK_ASSIGN;
break;
+ // Less-Than
+ case '<':
+ // Less-Than or Equal
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_LTE;
+ break;
+ }
+ ret = TOK_LT;
+ break;
+
+ // Greater-Than
+ case '>':
+ // Greater-Than or Equal
+ if( *File->CurPos == '=' ) {
+ File->CurPos ++;
+ ret = TOK_GTE;
+ break;
+ }
+ ret = TOK_GT;
+ break;
+
+ // Logical NOT
+ case '!':
+ ret = TOK_LOGICNOT;
+ break;
+ // Bitwise NOT
+ case '~':
+ ret = TOK_BWNOT;
+ break;
+
// Variables
// \$[0-9]+ or \$[_a-zA-Z][_a-zA-Z0-9]*
case '$':
// Default (Numbers and Identifiers)
default:
File->CurPos --;
+
// Numbers
if( isdigit(*File->CurPos) )
{
- while( isdigit(*File->CurPos) )
- File->CurPos ++;
ret = TOK_INTEGER;
+ if( *File->CurPos == '0' && File->CurPos[1] == 'x' ) {
+ File->CurPos += 2;
+ while(('0' <= *File->CurPos && *File->CurPos <= '9')
+ || ('A' <= *File->CurPos && *File->CurPos <= 'F')
+ || ('a' <= *File->CurPos && *File->CurPos <= 'f') )
+ {
+ File->CurPos ++;
+ }
+ }
+ else {
+ while( isdigit(*File->CurPos) )
+ File->CurPos ++;
+
+ // Decimal
+ if( *File->CurPos == '.' )
+ {
+ ret = TOK_REAL;
+ File->CurPos ++;
+ while( isdigit(*File->CurPos) )
+ File->CurPos ++;
+ }
+ // Exponent
+ if( *File->CurPos == 'e' || *File->CurPos == 'E' )
+ {
+ ret = TOK_REAL;
+ File->CurPos ++;
+ if(*File->CurPos == '-' || *File->CurPos == '+')
+ File->CurPos ++;
+ while( isdigit(*File->CurPos) )
+ File->CurPos ++;
+ }
+ }
break;
}
// Identifier
if( is_ident(*File->CurPos) )
{
+ ret = TOK_IDENT;
+
// Identifier
while( is_ident(*File->CurPos) || isdigit(*File->CurPos) )
File->CurPos ++;
// This is set later too, but we use it below
File->TokenLen = File->CurPos - File->TokenStr;
- ret = TOK_IDENT;
// Check if it's a reserved word
{