|
|
@@ -26,6 +26,7 @@ struct lexer_err {
|
|
|
|
|
|
struct lexer lexer_create(struct str in);
|
|
|
void lexer_read_char(struct lexer *l);
|
|
|
+char lexer_peek_char(struct lexer *l);
|
|
|
|
|
|
struct token lexer_next_token(struct lexer *l, struct lexer_err *err);
|
|
|
|
|
|
@@ -70,21 +71,45 @@ lexer_read_char(struct lexer *l)
|
|
|
++l->rpos;
|
|
|
}
|
|
|
|
|
|
+char
|
|
|
+lexer_peek_char(struct lexer *l)
|
|
|
+{
|
|
|
+ if ( l->rpos >= l->in.size ) {
|
|
|
+ return '\0';
|
|
|
+ }
|
|
|
+ return l->in.data[l->rpos];
|
|
|
+}
|
|
|
+
|
|
|
struct token
|
|
|
lexer_next_token(struct lexer *l, struct lexer_err *err)
|
|
|
{
|
|
|
#define _LEXER_CUR_CHAR str_slice(l->in, l->pos, l->pos+1)
|
|
|
+#define _LEXER_2_CHAR str_slice(l->in, l->pos, l->pos+2)
|
|
|
|
|
|
struct token t = TOKEN_ILLEGAL;
|
|
|
|
|
|
lexer_skip_whitespace(l);
|
|
|
|
|
|
switch ( l->c ) {
|
|
|
- case '=': t = token_create(TT_ASSIGN, _LEXER_CUR_CHAR); break;
|
|
|
+ case '=':
|
|
|
+ if ( lexer_peek_char(l) == '=' ) {
|
|
|
+ t = token_create(TT_EQ, _LEXER_2_CHAR);
|
|
|
+ lexer_read_char(l);
|
|
|
+ goto aft_swt;
|
|
|
+ }
|
|
|
+ t = token_create(TT_ASSIGN, _LEXER_CUR_CHAR);
|
|
|
+ break;
|
|
|
case ';': t = token_create(TT_SEMICOLON, _LEXER_CUR_CHAR); break;
|
|
|
case '(': t = token_create(TT_LPAREN, _LEXER_CUR_CHAR); break;
|
|
|
case ')': t = token_create(TT_RPAREN, _LEXER_CUR_CHAR); break;
|
|
|
- case '!': t = token_create(TT_BANG, _LEXER_CUR_CHAR); break;
|
|
|
+ case '!':
|
|
|
+ if ( lexer_peek_char(l) == '=' ) {
|
|
|
+ t = token_create(TT_NOT_EQ, _LEXER_2_CHAR);
|
|
|
+ lexer_read_char(l);
|
|
|
+ goto aft_swt;
|
|
|
+ }
|
|
|
+ t = token_create(TT_BANG, _LEXER_CUR_CHAR);
|
|
|
+ break;
|
|
|
case '/': t = token_create(TT_SLASH, _LEXER_CUR_CHAR); break;
|
|
|
case ',': t = token_create(TT_COMMA, _LEXER_CUR_CHAR); break;
|
|
|
case '*': t = token_create(TT_ASTERISK, _LEXER_CUR_CHAR); break;
|
|
|
@@ -125,7 +150,7 @@ lexer_next_token(struct lexer *l, struct lexer_err *err)
|
|
|
}
|
|
|
break;
|
|
|
}
|
|
|
-
|
|
|
+aft_swt:
|
|
|
lexer_read_char(l);
|
|
|
|
|
|
ret_ok:
|
|
|
@@ -134,6 +159,7 @@ ret_ok:
|
|
|
ret_invalid:
|
|
|
return TOKEN_ILLEGAL;
|
|
|
|
|
|
+#undef _LEXER_2_CHAR
|
|
|
#undef _LEXER_CUR_CHAR
|
|
|
}
|
|
|
|