feat: update tokens
This commit is contained in:
parent
db863b806e
commit
102b68fc27
75
DragonLisp.l
75
DragonLisp.l
|
|
@ -20,8 +20,9 @@ using token = DragonLisp::DLParser::token;
|
|||
%option yyclass="DragonLisp::DLScanner"
|
||||
%option verbose backup warn noyywrap c++ nounistd debug noline
|
||||
|
||||
float [+-]?[0-9]*[.][0-9]+([eE][+-][0-9]+)?
|
||||
int [+-]?(0[xX][0-9A-Fa-f]*|0[0-7]+|[1-9][0-9]*)
|
||||
id [a-zA-Z_][a-zA-Z_0-9]*
|
||||
int [0-9]+
|
||||
blank [ \t\v\r]
|
||||
comment ;.*$
|
||||
string \"[^\r\n]*\"
|
||||
|
|
@ -47,32 +48,65 @@ string \"[^\r\n]*\"
|
|||
{blank}+ {
|
||||
loc->step();
|
||||
std::printf("Skipping blank\n");
|
||||
return token::TOKEN_SPACE;
|
||||
};
|
||||
|
||||
\n+ {
|
||||
loc->lines(yyleng);
|
||||
loc->step();
|
||||
std::printf("Skipping newline\n");
|
||||
return token::TOKEN_SPACE;
|
||||
}
|
||||
|
||||
{float} {
|
||||
errno = 0;
|
||||
char* seq_end_ptr = nullptr;
|
||||
double n = strtod(yytext, &seq_end_str);
|
||||
if (errno == ERANGE)
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Float out of range: " + std::string(yytext));
|
||||
if (seq_end_ptr - yytext < yyleng)
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Invalid float scanned: [" + std::string(yytext, seq_end_ptr) + "], but provided [" + std::string(yytext) + "]");
|
||||
yylval->emplace<double>(n);
|
||||
std::printf("Scanned float: %lf\n", n);
|
||||
return TOKEN::TOKEN_FLOAT;
|
||||
}
|
||||
|
||||
{int} {
|
||||
errno = 0;
|
||||
char* seq_end_ptr = nullptr;
|
||||
int64_t n = strtoll(yytext, &seq_end_ptr, 0);
|
||||
if (errno == ERANGE)
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Integer out of range: " + std::string(yytext));
|
||||
if (seq_end_ptr - yytext < yyleng)
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Invalid integer scanned: [" + std::string(yytext, seq_end_ptr) + "], but provided [" + std::string(yytext) + "]");
|
||||
yylval->emplace<int64_t>(n);
|
||||
std::printf("Scanned integer: %lld\n", n);
|
||||
return token::TOKEN_INTEGER;
|
||||
};
|
||||
|
||||
"<=" {
|
||||
std::printf("Scanned <=\n");
|
||||
return token::TOKEN_LE;
|
||||
return token::TOKEN_LESS_EQUAL;
|
||||
};
|
||||
|
||||
">=" {
|
||||
std::printf("Scanned >=\n");
|
||||
return token::TOKEN_GE;
|
||||
return token::TOKEN_GREATER_EQUAL;
|
||||
};
|
||||
|
||||
"<" {
|
||||
std::printf("Scanned <\n");
|
||||
return token::TOKEN_LT;
|
||||
return token::TOKEN_LESS;
|
||||
};
|
||||
|
||||
">" {
|
||||
std::printf("Scanned >\n");
|
||||
return token::TOKEN_GT;
|
||||
return token::TOKEN_GREATER;
|
||||
};
|
||||
|
||||
"/=" {
|
||||
std::printf("Scanned !=\n");
|
||||
return token::TOKEN_NOT_EQUAL;
|
||||
};
|
||||
|
||||
"=" {
|
||||
|
|
@ -80,11 +114,6 @@ string \"[^\r\n]*\"
|
|||
return token::TOKEN_EQUAL;
|
||||
};
|
||||
|
||||
"/=" {
|
||||
std::printf("Scanned !=\n");
|
||||
return token::TOKEN_NE;
|
||||
};
|
||||
|
||||
"(" {
|
||||
std::printf("Scanned (\n");
|
||||
return token::TOKEN_LPAREN;
|
||||
|
|
@ -107,28 +136,26 @@ string \"[^\r\n]*\"
|
|||
|
||||
"*" {
|
||||
std::printf("Scanned *\n");
|
||||
return token::TOKEN_STAR;
|
||||
return token::TOKEN_MULTIPLY;
|
||||
};
|
||||
|
||||
"/" {
|
||||
std::printf("Scanned /\n");
|
||||
return token::TOKEN_SLASH;
|
||||
return token::TOKEN_DIVIDE;
|
||||
};
|
||||
|
||||
{int} {
|
||||
errno = 0;
|
||||
int64_t n = strtoll(yytext, nullptr, 10);
|
||||
if (errno)
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Invalid integer provided: " + std::string(yytext));
|
||||
yylval->emplace<int64_t>(n);
|
||||
std::printf("Scanned integer: %lld\n", n);
|
||||
return token::TOKEN_NUMBER;
|
||||
{id} {
|
||||
std::printf("Scanned identifier: %s\n", yytext);
|
||||
yylval->emplace<std::string>(std::string(yytext, yyleng));
|
||||
return token::TOKEN_IDENTIFIER;
|
||||
};
|
||||
|
||||
{id} { /* return DragonLisp::DLParser::make_IDENTIFIER(yytext, *loc); */ }
|
||||
. {
|
||||
throw DragonLisp::DLParser::syntax_error(*loc, "Invalid character: " + std::string(yytext));
|
||||
};
|
||||
|
||||
. { throw DragonLisp::DLParser::syntax_error(*loc, "Invalid character: " + std::string(yytext)); }
|
||||
|
||||
<<EOF>> { yyterminate(); }
|
||||
<<EOF>> {
|
||||
yyterminate();
|
||||
};
|
||||
|
||||
%%
|
||||
|
|
|
|||
66
DragonLisp.y
66
DragonLisp.y
|
|
@ -41,78 +41,36 @@ namespace DragonLisp {
|
|||
%define parse.assert
|
||||
|
||||
%token
|
||||
LE "<="
|
||||
GE ">="
|
||||
LESS_EQUAL "<="
|
||||
GREATER_EQUAL ">="
|
||||
LESS "<"
|
||||
GREATER ">"
|
||||
NOT_EQUAL "/="
|
||||
EQUAL "="
|
||||
NE "/="
|
||||
LT "<"
|
||||
GT ">"
|
||||
LPAREN "("
|
||||
RPAREN ")"
|
||||
PLUS "+"
|
||||
MINUS "-"
|
||||
STAR "*"
|
||||
SLASH "/"
|
||||
MULTIPLY "*"
|
||||
DIVIDE "/"
|
||||
SPACE
|
||||
;
|
||||
|
||||
%token END 0 "EOF"
|
||||
%token <int64_t> NUMBER "number"
|
||||
%token <double> FLOAT "float"
|
||||
%token <int64_t> INTEGER "integer"
|
||||
%token <std::string> STRING "string"
|
||||
|
||||
%type <DragonLisp::Token> basic_operator
|
||||
%type <DragonLisp::Token> arithmetic_operator
|
||||
%type <DragonLisp::Token> comparsion_operator
|
||||
%token <std::string> IDENTIFIER "identifier"
|
||||
|
||||
%define parse.error verbose
|
||||
|
||||
%%
|
||||
|
||||
S
|
||||
: R END
|
||||
|
||||
R
|
||||
:
|
||||
| R S-Expr
|
||||
| STRING { std::cout << "Scanned string -> " << $1 << std::endl; }
|
||||
|
||||
S-Expr
|
||||
: LPAREN basic_operator NUMBER NUMBER RPAREN {
|
||||
std::printf("Operator -> %d, LHS -> %lld, RHS -> %lld\n", int($2), $3, $4);
|
||||
std::printf("This is S-Expr!\n");
|
||||
}
|
||||
;
|
||||
|
||||
basic_operator
|
||||
: arithmetic_operator { $$ = $1; }
|
||||
| comparsion_operator { $$ = $1; }
|
||||
;
|
||||
|
||||
arithmetic_operator
|
||||
: PLUS { $$ = Token::PLUS; std::printf("I am plus +\n"); }
|
||||
| MINUS { $$ = Token::MINUS; std::printf("I am minus -\n"); }
|
||||
| STAR { $$ = Token::MULTIPLY; std::printf("I am star *\n"); }
|
||||
| SLASH { $$ = Token::DIVIDE; std::printf("I am slash /\n"); }
|
||||
;
|
||||
|
||||
comparsion_operator
|
||||
: LE { $$ = Token::LE; }
|
||||
| LT { $$ = Token::LT; }
|
||||
| GE { $$ = Token::GE; }
|
||||
| GT { $$ = Token::GT; }
|
||||
| EQUAL { $$ = Token::EQUAL; }
|
||||
| NE { $$ = Token::NE; }
|
||||
: END
|
||||
|
||||
%%
|
||||
|
||||
void DragonLisp::DLParser::error(const location_type& l, const std::string& msg) {
|
||||
std::cerr << "Error: " << msg << " at " << l << "\n";
|
||||
}
|
||||
|
||||
DragonLisp::DLParser::symbol_type make_NUMBER(const std::string& s, const DragonLisp::DLParser::location_type& loc) {
|
||||
try {
|
||||
int n = std::stoi(s);
|
||||
return DragonLisp::DLParser::make_NUMBER(n, loc);
|
||||
} catch (...) {
|
||||
throw DragonLisp::DLParser::syntax_error(loc, "Invalid integer provided: " + s);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue