*
This commit is contained in:
parent
b98af7bdde
commit
5991d9fef3
6 changed files with 52 additions and 2 deletions
1
README
1
README
|
|
@ -12,4 +12,5 @@
|
||||||
|
|
||||||
TODO:
|
TODO:
|
||||||
- [o] "#load" pragma
|
- [o] "#load" pragma
|
||||||
|
- [o better dip/keep (avoid using the retain stack for them)
|
||||||
- [ ] hand-rolled parser
|
- [ ] hand-rolled parser
|
||||||
|
|
|
||||||
11
examples/cat.grr
Normal file
11
examples/cat.grr
Normal file
|
|
@ -0,0 +1,11 @@
|
||||||
|
#load("std.grr")
|
||||||
|
|
||||||
|
def while {
|
||||||
|
swap dup bury >r >r
|
||||||
|
if: call dup
|
||||||
|
[r> dup >r call r> r> swap while]
|
||||||
|
[drop r> drop r> drop];
|
||||||
|
}
|
||||||
|
|
||||||
|
while: [stdin fgetline]
|
||||||
|
[print];
|
||||||
37
src/file.c
37
src/file.c
|
|
@ -1,5 +1,8 @@
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
#include "src/gc.h"
|
||||||
|
#include "src/object.h"
|
||||||
#include "string.h"
|
#include "string.h"
|
||||||
#include "userdata.h"
|
#include "userdata.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
|
|
@ -13,6 +16,11 @@ Ut userdata_file = {
|
||||||
};
|
};
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
|
I prim_file_stdin(Vm *vm) {
|
||||||
|
vm_push(vm, vm->stdin);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
I prim_file_stdout(Vm *vm) {
|
I prim_file_stdout(Vm *vm) {
|
||||||
vm_push(vm, vm->stdout);
|
vm_push(vm, vm->stdout);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
@ -29,13 +37,13 @@ I prim_file_fprint(Vm *vm) {
|
||||||
|
|
||||||
Ud *file_ud = userdata_unwrap(file_obj, &userdata_file);
|
Ud *file_ud = userdata_unwrap(file_obj, &userdata_file);
|
||||||
if (file_ud == NULL) {
|
if (file_ud == NULL) {
|
||||||
fprintf(stderr, "expected file object");
|
fprintf(stderr, "expected file object\n");
|
||||||
return VM_ERR_TYPE;
|
return VM_ERR_TYPE;
|
||||||
};
|
};
|
||||||
|
|
||||||
Str *str = string_unwrap(string_obj);
|
Str *str = string_unwrap(string_obj);
|
||||||
if (str == NULL) {
|
if (str == NULL) {
|
||||||
fprintf(stderr, "expected string");
|
fprintf(stderr, "expected string\n");
|
||||||
return VM_ERR_TYPE;
|
return VM_ERR_TYPE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -43,6 +51,31 @@ I prim_file_fprint(Vm *vm) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
I prim_file_fgetline(Vm *vm) {
|
||||||
|
O file_obj = vm_pop(vm);
|
||||||
|
I mark = gc_mark(&vm->gc);
|
||||||
|
gc_addroot(&vm->gc, &file_obj);
|
||||||
|
|
||||||
|
Ud *file_ud = userdata_unwrap(file_obj, &userdata_file);
|
||||||
|
if (file_ud == NULL) {
|
||||||
|
fprintf(stderr, "expected file object\n");
|
||||||
|
return VM_ERR_TYPE;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *lineptr = NULL;
|
||||||
|
size_t size;
|
||||||
|
I len = getline(&lineptr, &size, (FILE *)file_ud->data);
|
||||||
|
if (len == -1) {
|
||||||
|
vm_push(vm, NIL);
|
||||||
|
} else {
|
||||||
|
vm_push(vm, string_make(vm, lineptr, len));
|
||||||
|
}
|
||||||
|
free(lineptr);
|
||||||
|
|
||||||
|
gc_reset(&vm->gc, mark);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
static V finalizer(V *data) {
|
static V finalizer(V *data) {
|
||||||
FILE *f = (FILE *)data;
|
FILE *f = (FILE *)data;
|
||||||
if (f && f != stdin && f != stdout && f != stderr)
|
if (f && f != stdin && f != stdout && f != stderr)
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,8 @@
|
||||||
|
|
||||||
extern Ut userdata_file;
|
extern Ut userdata_file;
|
||||||
|
|
||||||
|
I prim_file_stdin(Vm *);
|
||||||
I prim_file_stdout(Vm *);
|
I prim_file_stdout(Vm *);
|
||||||
I prim_file_stderr(Vm *);
|
I prim_file_stderr(Vm *);
|
||||||
I prim_file_fprint(Vm *);
|
I prim_file_fprint(Vm *);
|
||||||
|
I prim_file_fgetline(Vm *vm);
|
||||||
|
|
|
||||||
|
|
@ -28,9 +28,11 @@ static I prim_printstack(Vm *vm) {
|
||||||
Pr primitives_table[] = {
|
Pr primitives_table[] = {
|
||||||
{".", prim_pprint},
|
{".", prim_pprint},
|
||||||
{".s", prim_printstack},
|
{".s", prim_printstack},
|
||||||
|
{"stdin", prim_file_stdin},
|
||||||
{"stdout", prim_file_stdout},
|
{"stdout", prim_file_stdout},
|
||||||
{"stderr", prim_file_stderr},
|
{"stderr", prim_file_stderr},
|
||||||
{"fprint", prim_file_fprint},
|
{"fprint", prim_file_fprint},
|
||||||
|
{"fgetline", prim_file_fgetline},
|
||||||
{NULL, NULL},
|
{NULL, NULL},
|
||||||
};
|
};
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@ V print(O o) {
|
||||||
printf("<quotation>");
|
printf("<quotation>");
|
||||||
break;
|
break;
|
||||||
case OBJ_STR: {
|
case OBJ_STR: {
|
||||||
|
// TODO: make this binary safe
|
||||||
Str *s = string_unwrap(o);
|
Str *s = string_unwrap(o);
|
||||||
char *escaped = malloc(s->len + 1);
|
char *escaped = malloc(s->len + 1);
|
||||||
memcpy(escaped, s->data, s->len);
|
memcpy(escaped, s->data, s->len);
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue