diff --git a/.editorconfig b/.editorconfig index f1094a0..7ecbc3d 100644 --- a/.editorconfig +++ b/.editorconfig @@ -1,7 +1,13 @@ root = true + [*] end_of_line = lf insert_final_newline = true + [*.{c,h,grr}] indent_style = space indent_size = 2 + +[meson.build] +indent_style = space +indent_size = 2 diff --git a/.gitignore b/.gitignore index 98db229..b4e10d9 100644 --- a/.gitignore +++ b/.gitignore @@ -1,5 +1,4 @@ -*.o -.cache -/growl +/.cache +/build /.envrc /compile_commands.json diff --git a/makefile b/makefile deleted file mode 100644 index 7e917b3..0000000 --- a/makefile +++ /dev/null @@ -1,11 +0,0 @@ -CC := cc -CFLAGS := -Og -g -std=c99 -Wpedantic -Wall -OBJS = chunk.o gc.o main.o object.o parser.o print.o vm.o vendor/mpc.o \ - vendor/yar.o - -growl: $(OBJS) - $(CC) -o growl $(OBJS) - -.PHONY: clean -clean: - rm -f growl $(OBJS) diff --git a/meson.build b/meson.build new file mode 100644 index 0000000..ebe2b98 --- /dev/null +++ b/meson.build @@ -0,0 +1,25 @@ +project( + 'growl', + 'c', + meson_version : '>= 1.3.0', + version : '0.1', + default_options : ['buildtype=debugoptimized', 'c_std=c99', 'warning_level=3'], +) + +sources = [ + 'src/chunk.c', + 'src/compile.c', + 'src/gc.c', + 'src/object.c', + 'src/parser.c', + 'src/print.c', + 'src/vm.c', + 'src/vendor/mpc.c', + 'src/vendor/yar.c', +] + +exe = executable( + 'growl', + 'src/main.c', sources, + install : true, +) diff --git a/object.c b/object.c deleted file mode 100644 index e69de29..0000000 diff --git a/print.c b/print.c deleted file mode 100644 index e69de29..0000000 diff --git a/print.h b/print.h deleted file mode 100644 index e69de29..0000000 diff --git a/shell.nix b/shell.nix index 7ecb062..873dc3e 100644 --- a/shell.nix +++ b/shell.nix @@ -3,5 +3,6 @@ pkgs.mkShell { buildInputs = with pkgs; [ clang-tools bear gdb tinycc + meson ninja ]; } diff --git a/chunk.c b/src/chunk.c similarity index 100% rename from chunk.c rename to src/chunk.c diff --git a/chunk.h b/src/chunk.h similarity index 100% rename from chunk.h rename to src/chunk.h diff --git a/common.h b/src/common.h similarity index 100% rename from common.h rename to src/common.h diff --git a/src/compile.c b/src/compile.c new file mode 100644 index 0000000..a510f7d --- /dev/null +++ b/src/compile.c @@ -0,0 +1,6 @@ +#include "compile.h" + + +I compile_program(mpc_ast_t *ast) { + +} diff --git a/src/compile.h b/src/compile.h new file mode 100644 index 0000000..2aa3751 --- /dev/null +++ b/src/compile.h @@ -0,0 +1,4 @@ +#include "common.h" +#include "vendor/mpc.h" + +I compile_program(mpc_ast_t *); diff --git a/gc.c b/src/gc.c similarity index 88% rename from gc.c rename to src/gc.c index 9ddf211..05043ce 100644 --- a/gc.c +++ b/src/gc.c @@ -3,7 +3,9 @@ #include #include +#include "chunk.h" #include "gc.h" +#include "object.h" #include "vendor/yar.h" #define ALIGN(n) (((n) + 7) & ~7) @@ -18,14 +20,14 @@ V gc_reset(Gc *gc, I mark) { gc->roots.count = mark; } static O copy(Gc *gc, Hd *hdr) { assert(infrom(gc, hdr)); - assert(hdr->type != TYPE_FWD); + assert(hdr->type != OBJ_FWD); Z sz = ALIGN(hdr->size); Hd *new = (Hd *)gc->to.free; gc->to.free += sz; memcpy(new, hdr, sz); - hdr->type = TYPE_FWD; + hdr->type = OBJ_FWD; O *obj = (O *)(hdr + 1); *obj = BOX(new); return *obj; @@ -40,7 +42,7 @@ static O forward(Gc *gc, O obj) { return obj; Hd *hdr = UNBOX(obj); - if (hdr->type == TYPE_FWD) { + if (hdr->type == OBJ_FWD) { O *o = (O *)(hdr + 1); return *o; } else { @@ -76,7 +78,13 @@ V gc_collect(Gc *gc) { Hd *hdr = (Hd *)scan; switch (hdr->type) { // TODO: the rest of the owl - case TYPE_FWD: + case OBJ_QUOT: { + Bc *chunk = (Bc *)(hdr + 1); + for (Z i = 0; i < chunk->constants.count; i++) + chunk->constants.items[i] = forward(gc, chunk->constants.items[i]); + break; + } + case OBJ_FWD: fprintf(stderr, "fatal GC error: forwarding pointer in to-space\n"); abort(); default: diff --git a/gc.h b/src/gc.h similarity index 100% rename from gc.h rename to src/gc.h diff --git a/main.c b/src/main.c similarity index 100% rename from main.c rename to src/main.c diff --git a/src/object.c b/src/object.c new file mode 100644 index 0000000..6a6de05 --- /dev/null +++ b/src/object.c @@ -0,0 +1,10 @@ +#include "object.h" + +I type(O o) { + if (o == NIL) + return TYPE_NIL; + if (IMM(o)) + return TYPE_NUM; + Hd *h = UNBOX(o); + return h->type; +} diff --git a/object.h b/src/object.h similarity index 76% rename from object.h rename to src/object.h index fe16d90..45d2239 100644 --- a/object.h +++ b/src/object.h @@ -11,7 +11,14 @@ #define ORD(x) ((O)(x) >> 1) enum { - TYPE_FWD, + OBJ_FWD = 2, + OBJ_QUOT, +}; + +enum { + TYPE_NIL = 0, + TYPE_NUM = 1, + TYPE_FWD = OBJ_FWD, }; typedef uintptr_t O; @@ -21,4 +28,6 @@ typedef struct Hd { U32 size, type; } Hd; +I type(O); + #endif diff --git a/parser.c b/src/parser.c similarity index 100% rename from parser.c rename to src/parser.c diff --git a/parser.h b/src/parser.h similarity index 99% rename from parser.h rename to src/parser.h index c0b3f2a..c991dd4 100644 --- a/parser.h +++ b/src/parser.h @@ -4,7 +4,6 @@ #include "common.h" #include "vendor/mpc.h" - V parser_init(V); V parser_deinit(V); diff --git a/src/print.c b/src/print.c new file mode 100644 index 0000000..c55cafe --- /dev/null +++ b/src/print.c @@ -0,0 +1,20 @@ +#include +#include + +#include "object.h" +#include "print.h" + +V print(O o) { + if (o == NIL) { + printf("nil"); + } else if (IMM(o)) { + printf("%" PRIdPTR, ORD(o)); + } else { + printf("", type(o), (void *)o); + } +} + +V println(O o) { + print(o); + putchar('\n'); +} diff --git a/src/print.h b/src/print.h new file mode 100644 index 0000000..ed86397 --- /dev/null +++ b/src/print.h @@ -0,0 +1,10 @@ +#ifndef PRINT_H +#define PRINT_H + +#include "common.h" +#include "object.h" + +V print(O); +V println(O); + +#endif diff --git a/vendor/mpc.c b/src/vendor/mpc.c similarity index 100% rename from vendor/mpc.c rename to src/vendor/mpc.c diff --git a/vendor/mpc.h b/src/vendor/mpc.h similarity index 100% rename from vendor/mpc.h rename to src/vendor/mpc.h diff --git a/vendor/yar.c b/src/vendor/yar.c similarity index 100% rename from vendor/yar.c rename to src/vendor/yar.c diff --git a/vendor/yar.h b/src/vendor/yar.h similarity index 100% rename from vendor/yar.h rename to src/vendor/yar.h diff --git a/vm.c b/src/vm.c similarity index 85% rename from vm.c rename to src/vm.c index 20df937..accbe82 100644 --- a/vm.c +++ b/src/vm.c @@ -1,5 +1,7 @@ #include "vm.h" #include "gc.h" +#include "print.h" +#include static I decode_sleb128(U8 **ptr) { I result = 0; @@ -45,16 +47,23 @@ V vm_run(Vm *vm, Bc *chunk, I offset) { U8 opcode; switch (opcode = *vm->ip++) { case OP_NOP: - break; - case OP_RETURN: - return; + continue; case OP_CONST: { I idx = decode_sleb128(&vm->ip); vm_push(vm, chunk->constants.items[idx]); break; } + case OP_RETURN: + goto done; } } +done: gc_reset(&vm->gc, mark); + // print stack :3 + for (O *i = vm->stack; i < vm->sp; i++) { + print(*i); + putchar(' '); + } + putchar('\n'); } diff --git a/vm.h b/src/vm.h similarity index 68% rename from vm.h rename to src/vm.h index 7da042d..a122267 100644 --- a/vm.h +++ b/src/vm.h @@ -9,8 +9,12 @@ enum { OP_NOP = 0, + OP_CONST, // Push constant to stack + OP_JUMP, // Relative jump + OP_JUMP_IF_NIL, // Relative jump if top-of-stack is nil + OP_DOWORD, + OP_CALL, OP_RETURN, - OP_CONST, }; #define STACK_SIZE 256