commit f9c6ca12138ede56cedd5810c44b775b09f047cb
parent b5bed264201e70639e4124790efe6043d93e42ae
Author: citbl <citbl@citbl.org>
Date: Thu, 14 May 2026 21:08:23 +1000
all or most operators
Diffstat:
4 files changed, 297 insertions(+), 3 deletions(-)
diff --git a/src/lexer.c b/src/lexer.c
@@ -77,6 +77,183 @@ Lexer* lexer_lex(Lexer* lex)
add_token(lex, t);
advance(lex);
continue;
+ case '!':
+ if (peek(lex) == '=') {
+ t.type = BANG_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = BANG;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '*':
+ if (peek(lex) == '=') {
+ t.type = STAR_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = STAR;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '/':
+ if (peek(lex) == '=') {
+ t.type = SLASH_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = SLASH;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '%':
+ if (peek(lex) == '=') {
+ t.type = PERCENT_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = PERCENT;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '&':
+ if (peek(lex) == '=') {
+ t.type = AMPERSAND_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '&') {
+ t.type = AMPERSAND_AMPERSAND;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = AMPERSAND;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+
+ case '|':
+ if (peek(lex) == '=') {
+ t.type = PIPE_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '|') {
+ t.type = PIPE_PIPE;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = PIPE;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '+':
+ if (peek(lex) == '+') {
+ t.type = PLUS_PLUS;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '=') {
+ t.type = PLUS_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = PLUS;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '-':
+ if (peek(lex) == '>') {
+ t.type = MINUS_GT;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '-') {
+ t.type = MINUS_MINUS;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '=') {
+ t.type = MINUS_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = EQ;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '<':
+ if (peek(lex) == '=') {
+ t.type = LT_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '<') {
+ t.type = LT_LT;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '-') {
+ t.type = LT_MINUS;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = LT;
+ add_token(lex, t);
+ advance(lex);
+ continue;
+ case '>':
+ if (peek(lex) == '=') {
+ t.type = GT_EQ;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ if (peek(lex) == '>') {
+ t.type = GT_GT;
+ add_token(lex, t);
+ advance(lex);
+ advance(lex);
+ continue;
+ }
+ t.type = GT;
+ add_token(lex, t);
+ advance(lex);
+ continue;
case ';':
t.type = SEMICOL;
add_token(lex, t);
diff --git a/src/lexer_tools.c b/src/lexer_tools.c
@@ -36,6 +36,12 @@ void print_tokens(Lexer* lex)
case RPAREN:
printf("RPAREN )\n");
break;
+ case BANG:
+ printf("BANG !\n");
+ break;
+ case BANG_EQ:
+ printf("BANG_EQ !=\n");
+ break;
case EQ:
printf("EQ =\n");
break;
@@ -48,6 +54,85 @@ void print_tokens(Lexer* lex)
case SEMICOL:
printf("SEMICOL ;\n");
break;
+ case LT_EQ:
+ printf("LT_EQ <=\n");
+ break;
+ case LT_LT:
+ printf("LT_LT <<\n");
+ break;
+ case LT_MINUS:
+ printf("LT_MINUS <-\n");
+ break;
+ case LT:
+ printf("LT <\n");
+ break;
+ case GT:
+ printf("GT >\n");
+ break;
+ case GT_EQ:
+ printf("GT_EQ >=\n");
+ break;
+ case GT_GT:
+ printf("GT_GT >>\n");
+ break;
+
+ case PLUS:
+ printf("PLUS +\n");
+ break;
+ case PLUS_PLUS:
+ printf("PLUS_PLUS ++\n");
+ break;
+ case PLUS_EQ:
+ printf("PLUS_EQ +=\n");
+ break;
+ case MINUS:
+ printf("MINUS -\n");
+ break;
+ case MINUS_EQ:
+ printf("MINUS_EQ -=\n");
+ break;
+ case MINUS_MINUS:
+ printf("MINUS_MINUS --\n");
+ break;
+ case MINUS_GT:
+ printf("MINUS_GT ->\n");
+ break;
+ case STAR:
+ printf("STAR *\n");
+ break;
+ case STAR_EQ:
+ printf("STAR_EQ *=\n");
+ break;
+ case PERCENT:
+ printf("PERCENT %%\n");
+ break;
+ case PERCENT_EQ:
+ printf("PERCENT_EQ %%=\n");
+ break;
+ case AMPERSAND:
+ printf("AMPERSAND &\n");
+ break;
+ case AMPERSAND_AMPERSAND:
+ printf("AMPERSAND_AMPERSAND &&\n");
+ break;
+ case AMPERSAND_EQ:
+ printf("AMPERSAND_EQ &=\n");
+ break;
+ case PIPE:
+ printf("PIPE |\n");
+ break;
+ case PIPE_PIPE:
+ printf("PIPE_PIPE ||\n");
+ break;
+ case PIPE_EQ:
+ printf("PIPE_EQ |=\n");
+ break;
+ case SLASH:
+ printf("SLASH /\n");
+ break;
+ case SLASH_EQ:
+ printf("SLASH_EQ /=\n");
+ break;
case IDENT:
printf("IDENT: %s\n", lex->tokens[i].lexeme.value);
break;
diff --git a/src/token.h b/src/token.h
@@ -20,8 +20,6 @@ typedef enum Token_Type {
BANG_EQ,
EQ_GT,
LT_EQ,
- LT_DASH,
- DASH_GT,
EQ,
BANG,
PLUS_EQ,
@@ -33,14 +31,21 @@ typedef enum Token_Type {
COLON,
SEMICOL,
PIPE,
+ PIPE_PIPE,
+ PIPE_EQ,
AMPERSAND,
+ AMPERSAND_EQ,
+ AMPERSAND_AMPERSAND,
CARET,
LT,
GT,
LT_LT,
GT_GT,
+ GT_EQ,
PLUS_PLUS,
MINUS_MINUS,
+ LT_MINUS,
+ MINUS_GT,
LIT_STRING,
LIT_DECIMAL,
LIT_INT,
@@ -49,7 +54,7 @@ typedef enum Token_Type {
} Token_Type;
typedef enum Keyword {
- IF = 135,
+ IF = 153,
ELSE,
WHILE,
OPT,
diff --git a/tests/lex_operators.sic b/tests/lex_operators.sic
@@ -0,0 +1,27 @@
+a > b
+a < b
+a >= b
+a <= b
+a == b
+a != b
+a >> b
+a << b
+a -> b
+a => b
+a <- b
+a <= b
+a--
+a++
+a -= b
+a += b
+a *= b
+a /= b
+a %= b
+a % b
+a & b
+a && b
+a &= b
+a | b
+a || b
+a |= b
+