summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorubq323 <ubq323@ubq323.website>2024-06-20 21:45:57 +0100
committerubq323 <ubq323@ubq323.website>2024-06-20 21:45:57 +0100
commitfa8891ffe017ae890f0ef07915cf8b52acd7304a (patch)
tree7478faee1981c1c98ee5e88e6c56529f83a64817
parent9a7d1b1d41f4b3bb3387e7bbe77105d0089803d0 (diff)
add true, false, nil keywords
-rw-r--r--com.c18
-rw-r--r--dis.c4
-rw-r--r--val.c5
-rw-r--r--val.h1
-rw-r--r--vm.c10
-rw-r--r--vm.h6
6 files changed, 37 insertions, 7 deletions
diff --git a/com.c b/com.c
index 4252ecd..3d891f7 100644
--- a/com.c
+++ b/com.c
@@ -10,10 +10,18 @@
static void compile_node(State *S, Chunk *ch, AstNode a) {
switch (a.ty) {
case AST_IDENT:;
- size_t len = strlen(a.as.str);
- ObjString *o = objstring_copy(S, a.as.str, len);
- chunk_wbc(S, ch, OP_GETGLOBAL);
- chunk_wbc(S, ch, chunk_wconst(S, ch, VAL_OBJ(o)));
+ char *ident = a.as.str;
+
+ if (0 == strcmp(ident, "true")) chunk_wbc(S, ch, OP_TRUE);
+ else if (0 == strcmp(ident, "false")) chunk_wbc(S, ch, OP_FALSE);
+ else if (0 == strcmp(ident, "nil")) chunk_wbc(S, ch, OP_NIL);
+ else {
+ // global read
+ size_t len = strlen(a.as.str);
+ ObjString *o = objstring_copy(S, a.as.str, len);
+ chunk_wbc(S, ch, OP_GETGLOBAL);
+ chunk_wbc(S, ch, chunk_wconst(S, ch, VAL_OBJ(o)));
+ }
break;
case AST_NUM:
chunk_wbc(S, ch, OP_LOADK);
@@ -104,6 +112,6 @@ int main() {
chunk_wbc(S, &ch, OP_PRINT);
chunk_wbc(S, &ch, OP_RET);
- runvm(S);
+ return runvm(S);
}
diff --git a/dis.c b/dis.c
index 0fb23f8..c4492df 100644
--- a/dis.c
+++ b/dis.c
@@ -44,6 +44,10 @@ void disasm_chunk(Chunk *ch) {
SIMPLE_INSTR(OP_SUB, "sub")
SIMPLE_INSTR(OP_MUL, "mul")
SIMPLE_INSTR(OP_DIV, "div")
+ SIMPLE_INSTR(OP_NIL, "nil")
+ SIMPLE_INSTR(OP_TRUE, "true")
+ SIMPLE_INSTR(OP_FALSE, "false")
+
}
}
#undef SIMPLE_INSTR
diff --git a/val.c b/val.c
index 40b7c5b..6f1dd9e 100644
--- a/val.c
+++ b/val.c
@@ -19,6 +19,11 @@ ObjString *objstring_copy(State *S, char *src, size_t len) {
return objstring_create(S, d, len, hash);
}
+ObjString *objstring_copy_cstr(State *S, char *str) {
+ size_t len = strlen(str);
+ return objstring_copy(S, str, len);
+}
+
ObjString *objstring_take(State *S, char *src, size_t len) {
uint32_t hash = hash_string(src, len);
ObjString *interned = ht_findstring(S, &S->strings, src, len, hash);
diff --git a/val.h b/val.h
index 4c84fd9..db0a789 100644
--- a/val.h
+++ b/val.h
@@ -49,6 +49,7 @@ typedef struct {
// Constructs a new objstring from the given C string,
// creating its own fresh copy of the data.
ObjString *objstring_copy(State *S, char *src, size_t len);
+ObjString *objstring_copy_cstr(State *s, char *str);
// Constructs a new objstring from the given C string,
// taking ownership of the provided data.
ObjString *objstring_take(State *S, char *src, size_t len);
diff --git a/vm.c b/vm.c
index 9f6ece6..205e0fd 100644
--- a/vm.c
+++ b/vm.c
@@ -46,10 +46,12 @@ Thread thread_new(State *S) {
}
-void runvm(State *S) {
+int runvm(State *S) {
Thread *th = S->th;
Chunk *ch = th->ch;
+ int status = 1;
+
disasm_chunk(ch);
#define RBYTE() (ch->bc.d[th->ip++])
@@ -63,6 +65,7 @@ void runvm(State *S) {
uint8_t instr = RBYTE();
switch (instr) {
case OP_RET:
+ status = 0;
printf("done!\n");
goto done;
break;
@@ -127,10 +130,15 @@ void runvm(State *S) {
ARITH_OP(OP_DIV, /)
#undef ARITH_OP
+ case OP_NIL: PUSH(VAL_NIL); break;
+ case OP_TRUE: PUSH(VAL_TRUE); break;
+ case OP_FALSE: PUSH(VAL_FALSE); break;
+
}
}
done:;
+ return status;
}
diff --git a/vm.h b/vm.h
index 859e207..e184426 100644
--- a/vm.h
+++ b/vm.h
@@ -49,8 +49,12 @@ typedef enum {
OP_GETGLOBAL,
OP_SETGLOBAL,
+
+ OP_TRUE,
+ OP_FALSE,
+ OP_NIL,
} Op;
-void runvm(State *S);
+int runvm(State *S);
#endif