1
0
Fork 0
LithOS3/lithos_c/src/token.c

165 lines
3.4 KiB
C

//-----------------------------------------------------------------------------
//
// Copyright © 2016-2017 Project Golan, David Hill
//
// Code by David Hill has been relicensed with consent.
//
// See "LICENSE.lithos3" for more information.
//
//-----------------------------------------------------------------------------
//
// Tokenizer.
//
//-----------------------------------------------------------------------------
#include "Lth_libinfo.h"
#if !LITHOS3_NO_TOKEN
#define _GNU_SOURCE
#include "Lth.h"
#include <ctype.h>
#include <string.h>
#include <ACS_ZDoom.h>
// Extern Functions ----------------------------------------------------------|
//
// Lth_TokenGet
//
void Lth_TokenGet(FILE *fp, Lth_Token *out)
{
char ch = fgetc(fp);
out->type = Lth_TOK_EOF;
if(out->str)
free(out->str), out->str = NULL;
switch(ch)
{
case '=': Lth_TokenSet(out, Equals); return;
case ';': Lth_TokenSet(out, Semico); return;
case ',': Lth_TokenSet(out, Comma ); return;
case '>': Lth_TokenSet(out, GT ); return;
case '<': Lth_TokenSet(out, LT ); return;
case '[': Lth_TokenSet(out, BrackO); return;
case ']': Lth_TokenSet(out, BrackC); return;
case '{': Lth_TokenSet(out, BraceO); return;
case '}': Lth_TokenSet(out, BraceC); return;
case '\n': Lth_TokenSet(out, LnEnd ); return;
case '-':
if(isdigit(Lth_fpeekc(fp))) break;
Lth_TokenSet(out, Minus);
return;
case '.':
if(isdigit(Lth_fpeekc(fp))) break;
Lth_TokenSet(out, Dot);
return;
}
if(isspace(ch))
{
ACS_BeginPrint();
do ACS_PrintChar(ch);
while((ch = fgetc(fp)) != EOF && (isspace(ch) && ch != '\n'));
if(ch != EOF) ungetc(ch, fp);
out->str = Lth_strdup_str(ACS_EndStrParam());
out->type = Lth_TOK_Space;
return;
}
if(ch == '"' || ch == '\'')
{
char beg = ch;
ACS_BeginPrint();
while((ch = fgetc(fp)) != beg && ch != EOF)
{
if(ch == '\\')
{
switch((ch = fgetc(fp)))
{
case '\\': ACS_PrintChar('\\'); break;
case 'C': ACS_PrintChar('\C'); break;
case 'n': ACS_PrintChar('\n'); break;
default: if(ch == beg) ACS_PrintChar(beg); break;
}
}
else
ACS_PrintChar(ch);
}
out->str = Lth_strdup_str(ACS_EndStrParam());
out->type = Lth_TOK_String;
return;
}
if(isdigit(ch) || ch == '.' || ch == '-')
{
ACS_BeginPrint();
do ACS_PrintChar(ch);
while((ch = fgetc(fp)) != EOF && (isalnum(ch) || ch == '.'));
if(ch != EOF) ungetc(ch, fp);
out->str = Lth_strdup_str(ACS_EndStrParam());
out->type = Lth_TOK_Number;
return;
}
if(Lth_isidenti(ch))
{
ACS_BeginPrint();
do ACS_PrintChar(ch);
while((ch = fgetc(fp)) != EOF && Lth_isidenti(ch));
if(ch != EOF) ungetc(ch, fp);
out->str = Lth_strdup_str(ACS_EndStrParam());
out->type = Lth_TOK_Identi;
return;
}
if(ch == EOF)
{
Lth_TokenSet(out, EOF);
return;
}
char chrseq[2] = {ch, '\0'};
out->str = Lth_strdup(chrseq);
out->type = Lth_TOK_ChrSeq;
}
//
// Lth_TokenName
//
char const *Lth_TokenName(Lth_TokenType type)
{
static char const *names[] = {
"None",
#define Lth_X(name) #name,
#include "Lth_token.h"
"EOF",
"Max"
};
return names[type];
}
#endif//LITHOS3_NO_TOKEN